[08NOIP универсальный сиденье группа строк]

http://ybt.ssoier.cn:8088/problem_show.php?pid=1943
[название] Описание
класса , когда всегда есть некоторые люди вокруг студентов и вокруг шептались друг с другом, то , что делает учитель начальной школы очень хлопотное дело. Тем не менее, учитель снег нашел некоторые интересные явления, когда студенты мест для сидения доработаны, ограничиваются только D шепнет , когда студенты в классе. Студенты в классе будет сидеть M строк и N столбцов, студенты позицию первой строки II колонке JJ сидя является (I, J), с тем чтобы облегчить студентам вне, при условии , что К поперечных каналов в классе, L продольный канал полосы. Итак, умный снег придумал способ, возможно, проблема студентов в классе шепчутся друг с другом может быть уменьшена: Она намерена изменить столы и стулья, столы и стулья , чтобы изменить положение канала между студентами, потому что если канал разделяющая два шептала студенты, они не будут шептать.

Не могли бы вы написать программу на снегу, дают наилучшую схему разделения каналов. Согласно этой схеме, минимальное количество студентов в классе шептала.

[Вход]
Первая линия, 55 отделены друг от друга пространством сертификата, а именно М, Н, К, L, D (2≤N, M≤1000,0≤K <М, 0≤L <N, D ≤2000) М, Н, К, L, D (2≤N, M≤1000,0≤K <М, 0≤L <N, D≤2000).

Следующая строка D, причем каждый ряд имеет четыре целых числа, разделенных пробелом. I-я строка из четырех сертификатов Xi, Yi, Pi, OiXi, Yi, Pi, Oi, выраженная сидячее положение (Xi, Yi) и (Pi, Oi) двух студентов будут шептать (до и после того, как они входят в смежных или гарантиях о смежном).

Входные данные для обеспечения уникальности лучших программ.

[Выход]
в общей сложности из двух линий.

Первая строка содержит целые числа К.К., а1, а2 ...... АК, a1 представляет собой строку между первой строки и a1 + 1, а2 первой строки и строки a2 + 1, ..., Ak первая строка и первый ряд Ak + 1 чтобы открыть путь между ними, где а <AI + 1, между каждые два целых числа, разделенных пробелом (без конца строки пробелами).

Вторая строка содержит L целых чисел, B1B2 ...... Б.Л., b1 представляет собой колонну между первым столбцом и b1 + 1, b2 между первого столбца и строки b2 + 1, ..., Bl, чтобы между первой строки и первого столбца Bl + 1 открытый канал, в котором би <Bi + 1, между каждыми двумя целыми числами, разделенным пробелом (без конца строки пробелов).

[Пример] входной сигнал
. 4 2. 3. 1. 5
. 4. 3. 4 2
2. 3. 3. 3
2 2. 5. 4
[Пример] Выход
2
2. 4

Тема немного долго, но этот вопрос рассматривается жадный + родом, проблема, которую необходимо решить, состоит: Найти первый K, L, прежде чем вертикальный ряд горизонтальных строк;

  • Как найти первую к горизонтали, то ясно, что большинство студентов говорят горизонтальные горизонтальное, отделившийся нужно только больше всего, поэтому необходимо найти наиболее горизонтальные выступая перед студентами к;
  • Как найти до л тандем, сопереживание.

Метод а: быстрый ряд жадные +

#include<bits/stdc++.h>
using namespace std;
#define N 1005
int aK[N], aL[N];//横排的前k个、纵排的前l个
int a1[N], b1[N];//横纵坐标出现的次数
int main(){
	int m, n, k, l, d, x1, y1, x2, y2;
	cin >> m >> n >> k >> l >> d;
	for(int i=1; i<=d; i++){//统计横纵坐标出现的次数
		cin >> x1 >> y1 >> x2 >> y2;
		if(x1 == x2)
			b1[(y1>y2)?y2:y1]++;
		else if(y1 == y2)
			a1[(x1>x2)?x2:x1]++;
	}
	for(int i=1; i<=k; i++){//通过比较大小,拿到a1数组(横坐标)中的前k值
		int mmax = 0, x;
		for(int j=1; j<=m; j++){
			if(a1[j] > mmax)
				mmax = a1[j], x = j;
		}
		aK[i] = x;
		a1[x] = 0;
	}
	for(int i=1; i<=l; i++){//通过比较大小,拿到b1数组(纵坐标)中的前l值
		int mmax = 0, x;
		for(int j=1; j<=n; j++){
			if(b1[j] > mmax)
				mmax = b1[j], x = j;
		}
		aL[i] = x;
		b1[x] = 0;
	}
	sort(aK+1, aK+k+1);
	sort(aL+1, aL+l+1);
	for(int i=1; i<=k; i++)
		cout << aK[i] << " ";
	cout << endl;
	for(int i=1; i<=l; i++)
		cout << aL[i] << " ";
	cout << endl;
	return 0;
}

Метод два: жадная структура упорядочения +

#include<bits/stdc++.h>
using namespace std;
#define N 1005
struct node{
	int t, x;
}aK[N], bL[N];
bool cmp_big(node p, node q){
	return p.t > q.t;
}
bool cmp_small(node p, node q){
	return p.x < q.x;
}
int main(){
	int m, n, k, l, d, x1, y1, x2, y2;
	cin >> m >> n >> k >> l >> d;
	for(int i=1; i<=d; i++){
		cin >> x1 >> y1 >> x2 >> y2;
		if(x1 == x2){
			bL[(y1>y2)?y2:y1].t++;//t:出现次数times
			bL[(y1>y2)?y2:y1].x = (y1>y2)?y2:y1;//x:出现的数
		}
		else if(y1 == y2){
			aK[(x1>x2)?x2:x1].t++;
			aK[(x1>x2)?x2:x1].x = (x1>x2)?x2:x1;
		}
	}
	sort(aK+1, aK+m+1, cmp_big);//按照出现次数从大到小排序,找到前k个
	sort(bL+1, bL+n+1, cmp_big);//按照出现次数从大到小排序,找到前l个
	sort(aK+1, aK+k+1, cmp_small);//将前k个按照x(数)从小到大排序
	sort(bL+1, bL+l+1, cmp_small);//将前l个按照x(数)从小到大排序
	for(int i=1; i<=k; i++)
		cout << aK[i].x << " ";
	cout << endl;
	for(int i=1; i<=l; i++)
		cout << bL[i].x << " ";
	cout << endl;
	return 0;
}
Опубликовано 15 оригинальных статей · вона похвала 10 · просмотров 209

рекомендация

отblog.csdn.net/qq_39053800/article/details/104249915
рекомендация