[21616][伯俊/BOJ]2805番の木を伐採


質問する



にゅうしゅつりょく



に答える


二分探索で問題を解くことができる.
mメートルの木を得るために、木材切断機に設置された最大高さHの問題.
上根が7 mの木を持ち去る必要がある場合、木の高さが20、15、10、17の場合、カッターに設けられた高さHを15とすると(20-15=5)+(17-15=2)=7となる.
そこで,Hを求めるために,1 mから木の最大高さまで,二分探索により,尚根がM mを持つ木のためにカッターに設けたHを求めることができる.
  • 分探索のために,左=1,右=ツリーの最大値に初期化した.
  • 分の探索で伐採された木の和がMより大きい場合、左の値はmid+1にリセットされる.
  • で二分探索を行った場合、伐採した樹木の和がM未満であれば、正しい値をmid-1にリセットする.
  • は少なくともmメートルの樹木を得るために設定された最大Hの問題であるため、伐採された樹木の和がmより大きい場合、最大midが正解である.
  • コード#コード#

    #include <bits/stdc++.h>
    using namespace std;
    typedef long long ll;
    
    int main()
    {
    	ios::sync_with_stdio(0);
    	cin.tie(0);
    
    	ll n, m, maxH = 0;
    	cin >> n >> m;
    	vector<ll> V(n);
    
    	for (int i = 0; i < n; ++i)
    	{
    		cin >> V[i];
    		maxH = max(maxH, V[i]);
    	}
    
    	ll left = 1, right = maxH, ans = 0;
    
    	while (left <= right)
    	{
    		ll mid = (left + right) / 2;
    		ll sum = 0;
    
    		for (int i = 0; i < n; ++i)
    		{
    			if(V[i] > mid)
    				sum += (V[i] - mid);
    		}
    
    		if (sum >= m) // 적어도 m미터의 나무를 가져갈려고함
    		{
    			ans = max(ans, mid);
    			left = mid + 1;
    		}
    		else
    			right = mid - 1;
    	}
    	cout << ans << '\n';
    }