这题,题目的意思是,有N个球从高度为H的地方落下,每一秒落下一个球,球与球之间和球与地板直接都是弹性碰撞,求T秒后的每个球的位置,也就是高度。
这题,跟Ants那题类似,也就是球与球碰撞可以当作不转换方向,继续按照原来的方向。也就是R = 0的时候,忽略半径,算出每一个球的位置,每一个球与地板碰撞后,会上升到原来的高度。先算出一次掉落需要t = sqrt(2 * H / g);每个球总共的时间T,总共的完整的来回有k = T / t次。
k为奇数,最终高度为H - g * (k * t + t - T)^ 2。
k为偶数,最终高度为H - g * (T - k * t)^ 2。
算出每一个球,排序后,就是各个球最终的位置,不过球的R为0.
因为R 大于等于1。所以,最后加上2 * i * R / 100.0就OK了,i是第i个球,因为R的单位是厘米,所以除以100.0。
下面的是AC的代码:
#include <iostream> #include <cmath> #include <cstdio> #include <algorithm> using namespace std; int N, H, R, T; const double g = 10.0; double y[105]; double fun(int t) { if(t < 0) return H; double d; double temp = sqrt(2 * H / g); int k = int(t / temp); if(k % 2 == 0) { d = t - temp * k; } else { d = k * temp + temp - t; } return H - g * d * d / 2; } void solve() { for(int i = 0; i < N; i++) { y[i] = fun(T - i); } sort(y, y + N); for(int j = 0; j < N; j++) { j == N - 1 ? printf("%.2lf\n", y[j] + 2 * R * j / 100.0) : printf("%.2lf ", y[j] + 2 * R * j / 100.0); } } int main() { int c; scanf("%d", &c); while(c--) { scanf("%d%d%d%d", &N, &H, &R, &T); solve(); } return 0; }
版权声明:本文为博主原创文章,未经博主允许不得转载。
原文地址:http://blog.csdn.net/qq_25425023/article/details/46695841