1. 程式人生 > 實用技巧 >Minimal Height Tree

Minimal Height Tree

連結 : http://codeforces.com/problemset/problem/1437/D

標籤 : trees greedy *1600

題意 :

用bfs序構造一棵樹, 保證每個根節點的子節點按升序排列, 問高度最低是多少.

思路 :

先處理出一個記錄每一個遞增序列中元素個數的陣列. 比如處理出 : 3 1 1 1 1 1 1. 在根節點下最多放3個子節點, 這是第一層, 然後第一層這三個節點又可以把後面3個1作為子節點, 作為第二層. 最後, 第二層這3個1又正好將最後3個1作為子節點, 作為第3層. 整個流程結束. 答案為 3.

思路感覺不難想到, 但是程式碼的實現細節需要仔細想好, 我在程式碼實現上就用了很長時間.

程式碼 :
#include <bits/stdc++.h>
using namespace std;
#define IO ios::sync_with_stdio(false);cin.tie(0); cout.tie(0)
inline int lowbit(int x) { return x & (-x); }
#define ll long long
#define pb push_back
#define PII pair<int, int>
#define fi first
#define se second
#define inf 0x3f3f3f3f
const int N = 2e5 + 7;
int a[N];

int main() {	
    IO;
    int _;
    cin >> _;
    while (_--) {
        int n, cnt = 0, ans = 1;
        vector<int> v;
        v.pb(0);
        cin >> n;
        for (int i = 1; i <= n; ++i) {
            cin >> a[i];
            if (a[i] > a[i - 1]) cnt++;
            else {
                v.pb(cnt);
                cnt = 1;
            }
        }
        v.pb(cnt);
        n = v.size() - 1;
        v[1]--;
        for (int i = 1; i <= n; ++i) v[i] += v[i - 1];
        int l = 0, r = 1, t;
        while (r < n) {
            t = r;
            r += v[r] - v[l];
            l = t;
            ans++;
        }
        cout << ans << endl;
    } 
    return 0;
}