洛谷 p1040 加分二叉樹
設乙個 n 個節點的二叉樹tree的中序遍歷為( 1,2,3,…,n ),其中數字 1,2,3,…,n 為節點編號。每個節點都有乙個分數(均為正整數),記第 i 個節點的分數為 di,tree及它的每個子樹都有乙個加分,任一棵子樹 subtree (也包含 tree 本身)的加分計算方法如下:
subtree 的左子樹的加分× subtree 的右子樹的加分+ subtree 的根的分數。
若某個子樹為空,規定其加分為 1 ,葉子的加分就是葉節點本身的分數。不考慮它的空子樹。
試求一棵符合中序遍歷為( 1,2,3,…,n )且加分最高的二叉樹 tree 。要求輸出;
(1) tree 的最高加分
(2) tree 的前序遍歷
輸入格式:
第 1 行: 1 個整數 n (n
第 2 行: n個用空格隔開的整數,為每個節點的分數(分數 <100 )。
輸出格式:
第 1 行: 1 個整數,為最高加分(ans ≤ 4,000,000,000 )。
第 2 行: n 個用空格隔開的整數,為該樹的前序遍歷。
輸入樣例#1: 複製
5輸出樣例#1: 複製5 7 1 2 10
1453 1 2 4 5
思路:用f[i][j]表示中序遍歷為 i 到 j 的一棵樹的最大加分
則:f[i][j]=max
用d[i][j]記錄區間[i,j]的根節點, write(i,j)輸出區間[i,j]這棵樹
則:write(i,j)==>wrie(i,d[i][j]-1)+d[i][j]+write(d[i][j]+1,j)
#include#define m 55view codeusing
namespace
std;
intn;
intf[m][m],d[m][m];
void write(int l, int
r) int
main()
f[1][0] = 1
;
for(int k = 2; k <= n; k++)
for(int s = 1; s+k-1
<= n; s++)
for(int e = s+k-1,j = s; j <= e; j++)
if(f[s][e] < f[s][j-1] * f[j+1][e] +f[j][j])
printf(
"%d\n
", f[1
][n]);
write(
1, n);
return0;
}
洛谷 P1040 加分二叉樹
題目描述 設乙個n個節點的二叉樹tree的中序遍歷為 1,2,3,n 其中數字1,2,3,n為節點編號。每個節點都有乙個分數 均為正整數 記第i個節點的分數為di,tree及它的每個子樹都有乙個加分,任一棵子樹subtree 也包含tree本身 的加分計算方法如下 subtree的左子樹的加分 su...
洛谷 P1040 加分二叉樹
題目描述 設乙個n個節點的二叉樹tree的中序遍歷為 1,2,3,n 其中數字1,2,3,n為節點編號。每個節點都有乙個分數 均為正整數 記第i個節點的分數為di,tree及它的每個子樹都有乙個加分,任一棵子樹subtree 也包含tree本身 的加分計算方法如下 subtree的左子樹的加分 su...
洛谷P1040 加分二叉樹
設乙個 n 個節點的二叉樹tree的中序遍歷為 1,2,3,n 其中數字 1,2,3,n 為節點編號。每個節點都有乙個分數 均為正整數 記第 i 個節點的分數為 di,tree 及它的每個子樹都有乙個加分,任一棵子樹 subtree 也包含 tree 本身 的加分計算方法如下 subtree 的左子...