算法 14.水晶问题

问题描述

和许多同龄女孩子一样,久莲也喜欢水晶球。

还有 10 天,就是心心念念的他生日了。

久莲希望把全世界最大最好看的水晶球送给他。

她找到了宝石收藏家亚瑟斯,希望能够寻求他的帮助。

亚瑟斯很快被打动了,拿出了精心收集的 n 块美丽的水晶石,这些水晶石初始是长宽高分别为 a, b, c 的长方体。亚瑟斯许诺久莲可以从中取走 1 块水晶石作为她礼物的原材料。

同时亚瑟斯有一种魔法,如果这两块长方形水晶石在某一个面能够完美的契合在一起(完美的契合是指这两个长方形面全等),那么可以将它们融合成一块完整的大石头,如果真的实现的话,那么久莲就可能打磨出更大的水晶球啦!

久莲太希望把最美最大的水晶球送给他了,你快帮帮她如何选择吧。

输入

第一行输入一个正整数 n 空格 左括号 1 小於等於 n 小於等於 10 的 5 次方 右括号;

接下来 n 行中,第 i 行输入三个正整数 a 下標 i 逗號 空格 b 下標 i 逗號 空格 c 下標 i 空格 左括号 1 小於等於 a 下標 i 逗號 空格 b 下標 i 逗號 空格 c 下標 i 小於等於 10 的 9 次方 右括号 表示第 i 块水晶石的长宽高。注意可能有两个长得一模一样的水晶石,但是在这种情况下还是将它们视作是两块不同的水晶石。

输出

第一行请输出一个正整数 k 空格 左括号 1 小於等於 k 小於等於 2 右括号,表示久莲选择的水晶球数量。

第二行请输出 k 个正整数,如果 k 等於 1,请输出一个正整数 x 空格 左括号 1 小於等於 x 小於等於 n 右括号 表示久莲选择的水晶石。如果 k 等於 2,则请输出两个正整数 x 逗號 空格 y 空格 左括号 1 小於等於 x 逗號 空格 y 小於等於 n 右括号 (用空格间隔),表示久莲希望亚瑟斯帮她将编号为 x 和 y 的水晶石融合成一块更大的水晶石,并选择用这块水晶石来打磨加工。请注意,这两块水晶石必须满足 “完美契合” 的条件,否则这个选择不合法。如果有多种最优的选择,则你可以输出任意一种合法的最优方案。

Hint
对于样例,如果久莲选择第六个水晶球,那么她可以打磨成半径为 r 等於 2.5 的水晶球,这是最优的选择。
这个题,稍微想想就有一个简化的思路了,就是需要排序两次。。其实仔细一想这个做法是有漏洞的。。不过还好测试数据没有在这里挖坑

样例

输入(1)

6
1 2 3
4 1 1
4 2 3
4 2 3
4 3 3
5 5 5

输出(1)

1
6

代码

#include <stdio.h>
#include <stdlib.h>//这是第十四题 水晶问题 
typedef struct{
	long long int a;
	long long int b;
	long long int c;
	int number;
} cube;//首先,设置一个叫做方体的结构体来存储所有的水晶的结构。 
cube crystal[100005],crystal2[100005];
int comp(const void* a,const void* b)
{
	return (*(cube*)b).c-(*(cube*)a).c;
}//在这里使用降序来给所有的长方体按照最短边排序 

int comp2(const void* e,const void* f)
{
	return (*(cube*)f).b-(*(cube*)e).b;
}//在这里给所有的长方体按照中长边的降序排序 
int main()
{
	long int n;
	long long int zu[3]={};
	scanf("%ld",&n);
	for(long int i=0;i<n;i++)
		{
			scanf("%lld",&zu[0]);
			scanf("%lld",&zu[1]);
			scanf("%lld",&zu[2]);
			long long int m;
			for(int p=1;p<=2;p++)//用一个冒泡排序来给每一个长方体的三边进行排序 
				{
					for(int q=0;q<3-p;q++)
						{
							if(zu[q]>zu[q+1])
								{
									m=zu[q];
									zu[q]=zu[q+1];
									zu[q+1]=m;
								}
						}
				}
			crystal[i].c=zu[0];
			crystal[i].b=zu[1];
			crystal[i].a=zu[2];
			crystal[i].number=i;//记录每一个长方体的数据 
		}
	qsort (crystal,n,sizeof(cube),&comp);//对所有的最短边进行降序排序 
	long int len=0;
	long long int max1=0;
	max1=crystal[0].c;//记录单个水晶可以雕刻出的最大水晶球 
	for(long int i=0;i<n;i++)
	{
		if(crystal[i].b<max1)
		{
			continue;
		}
		else
		{
			crystal2[len].a=crystal[i].a;
			crystal2[len].b=crystal[i].b;
			crystal2[len].c=crystal[i].c;
			crystal2[len].number=crystal[i].number;
			len++;
		}
	}//排除点所有不可能的长方体(也就是中长边长度小于单个水晶球最大值的长方体,因为我们在合并的时候一定要延长最短边才有意义) 
	long int p1,p2;
	long long int max2=0;
	long long int now=0;
	qsort (crystal2,len,sizeof(cube),&comp2);//对所有合格的长方体按照中长边的长度排序 
	for(long int i=0;i<len-1;i++)//为了防止超时,只用一次遍历,因为中长边已经按降序排好了,所以可以合并的水晶一定是相连的 
	{
		if(crystal2[i].a==crystal2[i+1].a&&crystal2[i].b==crystal2[i+1].b)
			{
				now=crystal2[i].c+crystal2[i+1].c;
				if(now>crystal2[i+1].b)
				{
					now=crystal2[i+1].b;
				}
				if(now>max2)
				{
					max2=now;
					p1=i;p2=i+1;
				}
			}
	}
	if(max1>max2)
	{
		printf("1\n");
		printf("%ld\n",crystal[0].number+1);
	}
	else
	{
		printf("2\n");
		printf("%ld %ld\n",crystal2[p1].number+1,crystal2[p2].number+1);
	}
	return 0;
}



  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
基于价值的强化学习问题可以使用以下算法进行解决: A. PPO算法 B. SARSA算法 C. DQN算法 D. 策略梯度算法 这些算法都是用于解决强化学习问题的,但是它们在解决问题的方式和原理上有所不同。以下是对每个算法的简要介绍: A. PPO算法(Proximal Policy Optimization)是一种基于策略梯度的算法,它通过优化策略函数来提高智能体的性能。PPO算法通过使用一种称为“重要性采样”的技术来更新策略函数,以平衡探索和利用的权衡。 B. SARSA算法(State-Action-Reward-State-Action)是一种基于值函数的算法,它通过估计每个状态-动作对的值来指导智能体的决策。SARSA算法使用一种称为“时序差分学习”的技术来更新值函数,以逐步改进智能体的策略。 C. DQN算法(Deep Q-Network)是一种基于值函数的算法,它使用深度神经网络来估计状态-动作对的值函数。DQN算法通过使用一种称为“经验回放”的技术来训练神经网络,并使用一种称为“ε-贪婪策略”的技术来指导智能体的决策。 D. 策略梯度算法是一类基于策略梯度的算法,它通过直接优化策略函数来提高智能体的性能。策略梯度算法使用一种称为“策略梯度定理”的技术来更新策略函数,以最大化期望回报。 综上所述,以上四种算法都可以用于解决基于价值的强化学习问题,但它们在解决问题的方式和原理上有所不同。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值