㈠ c语言贪心算法智力大冲浪与花生采摘两题
都是用C++写的,不建议只用纯C语言
#include <iostream>
#include <fstream>
#include <algorithm>
using namespace std;
struct Riddle {
int time;
int money;
};
struct gt{
bool operator()(Riddle& opl, Riddle& opr){
return opl.money > opr.money;
}
};
int main()
{
int m, n;
ifstream fin("riddle.in");
fin >> m >> n;
Riddle * riddles = new Riddle[n];
for (int i=0; i<n; ++i) {
fin >> riddles[i].time;
}
for (int i=0; i<n; ++i) {
fin >> riddles[i].money;
}
sort(riddles, riddles+n, gt() );
int * ridorder = new int[n];
for (int i=0; i<n; ++i) {
ridorder[i] = 0;
}
for (int i=0; i<n; ++i) {
int j;
for (j=riddles[i].time-1; j>=0 && ridorder[j]!=0; --j) {}
if (j >= 0) ridorder[j] = 1;
else m -= riddles[i].money;
}
cout << m << endl;
}
#include <iostream>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <cmath>
#include <algorithm>
using namespace std;
#define maxn 55
struct Peanut
{
int x, y, num;
}peanut[maxn * maxn];
int n, m, t, pcount;
bool operator < (const Peanut &a, const Peanut &b)
{
return a.num > b.num;
}
void input()
{
pcount = 0;
scanf("%d%d%d", &n, &m, &t);
for (int i = 0; i < n; i++)
for (int j = 0; j < m; j++)
{
int a;
scanf("%d", &a);
if (a)
{
peanut[pcount].x = i + 1;
peanut[pcount].y = j + 1;
peanut[pcount].num = a;
pcount++;
}
}
}
void work()
{
int nowtime = peanut[0].x + 1;
if (nowtime + peanut[0].x > t)
{
printf("0\n");
return;
}
int ans = peanut[0].num;
for (int i = 1; i < pcount; i++)
{
nowtime += abs(peanut[i].x - peanut[i - 1].x) + abs(peanut[i].y - peanut[i - 1].y) + 1;
if (nowtime + peanut[i].x > t)
break;
ans += peanut[i].num;
}
printf("%d\n", ans);
}
int main()
{
//freopen("t.txt", "r", stdin);
int t;
scanf("%d", &t);
while (t--)
{
input();
sort(peanut, peanut + pcount);
work();
}
return 0;
}
㈡ C语言 贪心算法求背包问题
是你的冒泡排序出了问题~
你吧 原来的1-2-3号按照东西的价值重新排列现在的1-2-3对应原来的2-1-3了
所以 你输出的时候是按 1-2-3输出的话 就等于第一个是原来的X2 第二个是X1第三个是X3
而且你的冒泡排序用错了 只比较了 P[0]/K[0]和P[1]/K[1] P[1]/K[1]和P[2]/K[2]
周一我去学校帮你重新改改 我家的机器没有C++
周一晚上我会上传答案~我最近正好也要做算法的作业~
#include <stdio.h>
#include <math.h>
#define N 50
float find(float p[N],float w[N],float x[N] ,float M,int n) /*先放单位价值量大的物体,再考虑小的物体*/
{
int i;
float maxprice;
for (i = 0; i < n; i++)
x[i] = 0;
i = 0;
maxprice=0;
while (i < n && w[i] < M)
{
M=M-w[i];
x[i] =w[i]; /* 表示放入数量 */
maxprice=maxprice+p[i];
x[n-1]=M;
i++;
}
if (i < n &&M> 0)
{
maxprice=maxprice+p[i]*x[i]/w[i];
i++;
}
return maxprice;
}
int main()
{
int n,flag=1;
float temp,M,w[N],p[N],x[N];
int a[N],b[N];
int k,j,l=0;
printf(
㈢ C语言中prime的作用
prime的作用就是判断一个数是否为素数(也称“质数”)。
例如:
#include<stdio.h>
intIsPrime(intn)
{
if(n<=1)return0;
if(n%2==0)returnn==2;
for(inti=3;;i+=2)
{
if(i>n/i)break;//等价于i*i>n,不用开方
if(n%i==0)return0;
}
return1;
}
intmain()
{
for(intn=100;n<=300;n++)
if(IsPrime(n))
printf("%4d",n);
return0;
}
prime算法
prime是以点为基础出发进行检索最小生成树的一种贪心算法。
思想:
将所有的点分成两类,一类是已经放到碗里的,另一类是还没有有放到碗里的,可以通过一个数组bool visit[]来记录这个点到底是属于第一类还是属于第二类之后每一个周期索要进行的操作,找出一一定范围内路径的的范围的最小值。
所有的从第一类点直接连接到第二类点的边将最小的边记录下来(这个也就是生成树中的一条边)将这个新边(这个一个连接第一类点和第二类点的边)连到的那个第二类点归类到第一类点中,之后重复这个操作,最终消灭所有的第二类点。
假设有n个节点,我最初给出一个点,以这个点开始进行搜索,这个时候该点为第一类点,其余n-1个点为第二类点。之后进行n-1次操作,一共选出了n-1个边(符合树的性质),构成了最小生成树。