uva 1346

题目链接:uva 1346 - Songs


题目大意:John Doe 是一个著名的DJ,现在他有n首播放个曲, 每首歌曲有识别符key,歌曲长度l,以及播放频率q。想在John Doe 想将磁带上的歌曲重新排列,方便播放,播放所有歌曲有一个复杂度的计算∑(1≤i≤n)q[i] * ( ∑(1≤j≤i)l[j] ), 然后给出S,请输出重新排列后的第S首歌的识别码。


解题思路:为了使得复杂度越小,很明显的曲目长度小的要放前面,播放频率小的要放后面,所以每首歌增加一个k = l / q,即k越小的越在前。如果两个k值相同的话,前后是没有差别的。

证:l[i] = L, q[i] = Q, l[j] = K * L, q[j] = K * Q.

l[i] * q[i] + (l[i] + l[j]) * q[j] = (K * K + K + 1) Q * L = l[j] * q[j] + (l[i] + l[j]) * q[i].


#include <stdio.h>
#include <string.h>
#include <algorithm>

using namespace std;

const int N = 70000;

struct song {
	int key;
	int l;
	double q;
	double k;
}s[N];
int n, S;

void init() {
	memset(s, 0, sizeof(s));
	for (int i = 0; i < n; i++) {
		scanf("%d%d%lf", &s[i].key, &s[i].l, &s[i].q);
		s[i].k = s[i].l / s[i].q;
	}
	scanf("%d", &S);
}

bool cmp(const song& a, const song& b) {
	return a.k - b.k < 1e-9;
}

int main () {
	while (scanf("%d", &n) == 1) {
		init();
		sort(s, s + n, cmp);
		printf("%d
", s[S - 1].key);
	}
	return 0;
}


原文地址:https://www.cnblogs.com/riasky/p/3469148.html