「雜題亂刷2」CF827B

wangmarui發表於2024-10-03

題目連結

CF827B

解題思路

假設樹以 \(1\) 為根,考慮先將 \(k\) 個深度為 \(1\) 的節點,然後我們就可以將剩餘的節點掛在目前的葉子節點上,但是如果一個葉子節點掛了 \(2\) 個葉子節點的話,那麼這樣葉子節點數目你一定不能使葉子節點減少,因此一個葉子節點最多只能往下掛一個節點,因此你直接用優先佇列維護即可。

時間複雜度 \(O(n \log n)\)

參考程式碼

點選檢視程式碼
#include<bits/stdc++.h>
using namespace std;
//#define map unordered_map
#define re register
#define ll long long
#define forl(i,a,b) for(re ll i=a;i<=b;i++)
#define forr(i,a,b) for(re ll i=a;i>=b;i--)
#define forll(i,a,b,c) for(re ll i=a;i<=b;i+=c)
#define forrr(i,a,b,c) for(re ll i=a;i>=b;i-=c)
#define pii pair<ll,ll>
#define mid ((l+r)>>1)
#define lowbit(x) (x&-x)
#define pb push_back
#define IOS ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);
#define endl '\n'
#define QwQ return 0;
#define db long double
#define ull unsigned long long
#define lcm(x,y) (1ll*(x)/__gcd(x,y)*(y))
#define Sum(x,y) (1ll*((x)+(y))*((y)-(x)+1)/2)
#define x first
#define y second
#define aty cout<<"Yes\n";
#define atn cout<<"No\n";
#define cfy cout<<"YES\n";
#define cfn cout<<"NO\n";
#define xxy cout<<"yes\n";
#define xxn cout<<"no\n";
#define printcf(x) x?cout<<"YES\n":cout<<"NO\n";
#define printat(x) x?cout<<"Yes\n":cout<<"No\n";
#define printxx(x) x?cout<<"yes\n":cout<<"no\n";
#define maxqueue priority_queue<ll>
#define minqueue priority_queue<pii,vector<pii>,greater<pii>>
#define bug cout<<"---------------------------------------\n";
//ll pw(ll x,ll y,ll mod){if(y==0)return 1;if(x==0)return 0;ll an=1,tmp=x;while(y){if(y&1)an=(an*tmp)%mod;tmp=(tmp*tmp)%mod;y>>=1;}return an;}
template<typename T1,typename T2>bool Max(T1&x,T2 y){if(y>x)return x=y,1;return 0;}
template<typename T1,typename T2>bool Min(T1&x,T2 y){if(y<x)return x=y,1;return 0;}
ll _t_;
void _clear(){}
ll n,m;
minqueue q;
vector<pii>ans;
ll a[200010];
ll k;
void solve()
{
    _clear();
	cin>>n>>m;
	if(m==2)
	{
		cout<<n-1<<endl;
		forl(i,1,n-1)
			cout<<i<<' '<<i+1<<endl;
		return ;
	}
	forl(i,2,m+1)
		q.push({1,i}),ans.pb({1,i}),a[++k]=1;
	forl(i,m+2,n)
	{
		pii now=q.top();
		q.pop();
		ans.pb({now.y,i});
		a[++k]=now.x+1;
		q.push({now.x+1,i});
	}
	sort(a+1,a+1+k);
	cout<<a[k]+a[k-1]<<endl;
	for(auto i:ans)
		cout<<i.x<<' '<<i.y<<endl;
}
int main()
{
//    freopen("tst.txt","r",stdin);
//    freopen("sans.txt","w",stdout);
    IOS;
    _t_=1;
  //  cin>>_t_;
    while(_t_--)
        solve();
    QwQ;
}