1. 程式人生 > 其它 >School Personal Contest #1 (Winter Computer School 2010/11) - Codeforces Beta Round #38 (ACM-ICPC Rules)

School Personal Contest #1 (Winter Computer School 2010/11) - Codeforces Beta Round #38 (ACM-ICPC Rules)

比賽連結:

https://codeforces.com/contest/38

D. Vasya the Architect

題目大意:

\(n\) 個立方體,給了每一個立方體在 \(xoy\) 面上投影的對角座標,按照給定的順序,依次往上疊立方體,問在保持平衡不到的狀態下,最多能疊多少個立方體。

思路:

對於第 \(i\) 個立方體,需要判斷的是它的重心是否落在下面立方體的投影內,即求重心公式,判斷是否能保持平衡。
\(k\) 個物品的疊加後的重心落在 \(( (x[1] * w[1] + x[2] * w[2] + ... + x[k] * w[k]) / (w[1] + w[2] + ... + w[k]), (y[1] * w[1] + y[2] * w[2] + ... + y[k] * w[k]) / (w[1] + w[2] + ... + w[k]))\)


\(w[i]\) 為第 \(i\) 個物品的重量,\(x[i]\) 為第 \(i\) 個物品重心的橫座標,\(y[i]\) 為第 \(i\) 個物品重心的縱座標。

程式碼:

#include <bits/stdc++.h>
using namespace std;
const int N = 110;
struct node{
	double x1, y1, x2, y2, x, y, w;
}a[N];
int n;
void solve(){
	for (int i = 0; i < n; i ++ ){
		double x = a[i].x * a[i].w, y = a[i].y * a[i].w, w = a[i].w;
		for (int j = i - 1; j >= 0; j -- ){
			if (x / w < a[j].x1 || x / w > a[j].x2 || y / w < a[j].y1 || y / w > a[j].y2){
				cout << i << "\n";
				return;
			}
			x += a[j].x * a[j].w;
			y += a[j].y * a[j].w;
			w += a[j].w;
		}
	}
	cout << n << "\n";
}
int main(){
	cin >> n;
	for (int i = 0; i < n; i ++ ){
		cin >> a[i].x1 >> a[i].y1 >> a[i].x2 >> a[i].y2;
		a[i].x = (a[i].x1 + a[i].x2) / 2.0;
		a[i].y = (a[i].y1 + a[i].y2) / 2.0;
		if (a[i].x1 > a[i].x2) swap(a[i].x1, a[i].x2);
		if (a[i].y1 > a[i].y2) swap(a[i].y1, a[i].y2);
		double t = a[i].y2 - a[i].y1;
		a[i].w = t * t * t;
	}
	solve();
	return 0;
}