誕生日ケーキ
トピック:
7月17日はMr.Wの誕生日は、ACM-木はM層Nπ誕生日ケーキを作成するには、このボリュームについて、それぞれの層がシリンダです。
番号i(1 <= I <=のボトムアップから提供 M) 半径Ri、円筒高さHIで層ケーキ。私は<M、必要Riを> Riを+ 1、こんにちは>こんにちは+ 1をするとき。
ケーキバタリングに、コスト削減が可能であり、我々は最も小さいQ.の面積ケーキ(除く底面下の最下層)の外面をしたいです
Q =Sπのように
プログラム所与の対NおよびMは、ケーキレシピプログラム(適切な値Ri及びHi)に、Sの最小値を見つけます
(Q付加、上記のすべてのデータは、すべての正の整数です)
入力
2つの行があり、最初の行のN(Nは<= 10000)、N [PI]で作られるべきケーキの体積を表し、第2列M(M <= 20)、ケーキM.の層の数を示します
出力
一つだけの行は、正の整数S(無溶液はS = 0でない場合)です。
サンプル入力
100
2
サンプル出力
68
ヒント
円筒式
容積=π・RのV 2 H
側の領域A「=2πRH
の底面積π・R = A 2
アイデア:
DFS層の数に応じている知っていることは容易です。層の条件と体積条件の数が満たされた場合、答えは最小出力を見つけることができます。ちょうどそれから、このトピックを書きたかったのはなぜ?このトピックは一見リラックスした時間が必要ですが、現実には、人々が血を吐くしたいので。DFSは、特に剪定用OJ hnust要件に、剪定を大量に書き出す必要があるだけで......あまりにも厳格です。三つのカテゴリーの剪定のための主要な必要性があります。
1)N + MINV [M - 1]> Nを超えるN、カット場合、結果と残りの層の体積が最小ケーキで製造することができる、ケーキの現在の体積を計算しました。
表面積の結果は、少なくともケーキ(ANS)場合の結果を生成することができる場合2)の和+分[M-1]> ANSは、残りの層と一緒に、ケーキの現在の表面積を算出した前回算出以上、カット。
両方呼ばれる残りの容積の表面積が必要とされるように、DV、S-sumv N:3)合計+ 2 *(NN)/ R> = ANS数式が導出されます
S = 2 * ND * HI * R 2 +(I-1)* H(I-1)+ ...> = 2 * ND * HI * RI / R + 2 * R(I-1)* H( I-1)* R(I-1)/ R + ...
= 2 * DV / R(iはM-1から採取した、rは現在の半径RI / R <1です)
また、最小の表面積S = 2 *(N-和)/ R、S及び最小の表面積が合計が依然として大きいの検索を続行しないであろうANSより検索された場合を与えるために必要とされます
(例えば、データhnustで提供)場合には、まだ時間をオーバーランした場合は第四の時間を剪定する必要があります。
4)現在の体積を算出する、ケーキの最大可能量を加算した結果は、N、カット未満です。これは兄の考え方に基づいている、はみ出さないでください、あなたはそれを見つけることができます
ACコード:
#include <ビット/ STDC ++ H> 使用して名前空間STDを、 INTは H、R、N、M、分[ 25 ]、MINV [ 25 ]。 CONST INT INF = 1 << 30 。 int型 ANS = infファイル。 int型の合計= 0 ; ボイド DFS(INT R、INT H、INT nは、整数 M、INT 合計) { 場合(Mの== 0 ) { 場合(N == N &&和< ANS) { ANS =和。 // COUT << R <<」「<< H << ENDL。 } を返します。 } もし、(N + MINV [M- 1 ]> N ||和+分[M- 1 ]> ANS ||和+ 2 *(NN)/ R> = ANS) のリターン; 以下のために(int型 I = R- 1 ; I> = M; i-- ) { int型 JL = I *はIを、 もし(M == M) 合計 = JL。 INT MAXH =((NN-MINV [M- 1 ])/(私を*)<H- 1)?(NN-MINV [M- 1 ])/(私は):H- 1; について(INT J = MAXH; J> = M、J、 ) { DFS(I、J、N- + JL * J、M- 1、SUM + 2 * I *はJの); } } } int型のmain() { MINV [ 0 ] = 0 ; 分[ 0 ] = 0 ; のための(INT I = 1。 ;私は= < 20であり、Iは++)// 可能な値の上面下方最小容積と表面積から算出 { // 上から(すなわちj番目の層の確立時に、i番目の層の最小体積[i]は第一層のMINV)の半径と高さJある MINV [I] = MINV [I-1 ] + I * I *はI; 分[I] =分[I- 1 ] + 2 * I *はIであり; } ながら(scanfの(" %のDの%のD "、&N、&M)== 2 ) { ANS = INFは、 int型 =のRmaxは(INT)SQRT((ダブル)Nを); // Rmaxとの最大半径の初期半径底SQRTに(N-) INT NのHmaxを=; // 初期のN-最大高さHmaxを DFS(のRmaxは、Hmaxとの、0、M、0 ); IF(ANS == INF) COUT<< 0 << てendl; 他の coutの << ANS << てendl; } 戻り 0 。 }