2024牛客暑期多校训练营8 J Haitang and Triangle

链接:登录—专业IT笔试面试备考平台_牛客网
来源:牛客网
 

题目描述

Given two integers n,m\textstyle n,m, construct a permutation of length  n that satisfies the following conditions.

  • There are exactly m subintervals of length 3 such that the numbers in these subintervals form a (non-degenerate) triangle.

输入描述:

Each test contains multiple test cases. The first line contains an integer T\textstyle TT (1≤T≤10^{5}) — the number of test cases. The description of the test cases follows.

The first and only line of each test case contains two integers  n andm (3≤n≤3×105, 0≤m≤n−2) — the length of permutation and the target subintervals.

It is guaranteed that the sum of n\textstyle n over all test cases does not exceed 3×10^{5}.

输出描述:

For each test case, print one line.

If such a pair of permutations exists, print n integers pi​, representing the permutation you have constructed. Otherwise, print “-1”.

示例1

输入

5
4 0
4 1
4 2
6 2
11 5

输出

3 1 2 4
1 2 3 4
-1
5 2 4 3 1 6
11 2 10 3 1 6 8 4 5 7 9

题目大意:构造一个长度为 n 的数组(数组里的值是 [ 1 , n ] 里的数且不重复),使得有 m 个长度为三的子区间,这些区间里的三个值看作三角形的三条边,并要满足构成三角形这个条件。

思路:因为有 1 这个值,它与任意两个值都不能构成三角形,所以 m=n-2 的时候输出 -1 。 

先将这 n 个数倒序赋值给数组,这个时候的满足题意的个数是最多的时候,即 n - 3 个区间能构成三角形,以数组第 m 个数开始为分界线,分成两半,左边一半可以直接输出,右边一半还要处理,假如右边一半下标从 i = 1 开始记录,定义三个起点,分别用 a =(n-m)表示剩下数组中最大的数,b = a -ceil ( ( n - m )/3.0) 表示剩下数组中中等大小的数,c = 1 表示剩下数组中最小的数,先后输出 a , b , c 。 a ,b 出现过以后自减,c出现过以后自增,直至跑完数组。(放完第一轮之后就已经有m个区间满足题意,用 1 分割,1 后面的值必定不能构成三角形)。

#include<bits/stdc++.h>
using namespace std;
#define int long long
#define endl '\n'
#define IOS ios::sync_with_stdio(false);cin.tie(0);cout.tie(0);
int s[300005];
signed main()
{
	IOS
	int t;
	cin >> t;
	while(t--){
		int n,m;
		cin >> n >> m;
		if(m==n-2){
			cout << -1 << endl;
			continue;
		}
		for(int i=1;i<=m;i++){
			s[i]=n-i+1;
		}
		int a=n-m,b=a-ceil((n-m)/3.0),c=1;
		for(int i=1;i+m<=n;i++){
			if(i%3==0) s[i+m]=c,c++;
			else if(i%3==1) s[i+m]=a,a--;
			else s[i+m]=b,b--;
		}
		for(int i=1;i<=n;i++){
			cout << s[i] << " ";
		}
		cout << endl;
	}
	return 0;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值