基本的なアイデアやアルゴリズム(*)大物は(ない非常に詳細な話をしているここでのポイントここでは、)小さいが、非常に実用的な最適化です。
唯一の一歩ACから見てみることができ
「アルゴリズムコンテストは、ステップアップガイド」124ページの「評価の評価機能は、将来の実際の値よりも大きくすることはできません」書き込みますが、この問題では、わずかな増加評価額が大幅に運用効率プログラムを向上させることができます
評価関数を最適化高い係数を用いて行われている間、高速最適化効率前後のすべての変更がほぼ倍増します
各ノブの目標状態から(1)及び(全体を引き継い)2で割った差の和:一般的な評価関数
ブール演算子<(constのE&A)のconst { +(AV >> 1)+(AV&1)としてリターンS +(V >> 1)+(V&1)>。 }
注意:
1は、Sが操作された現在の状態の数を意味し、Vは、各ノブと(評価関数)の目標状態との差を表します
(おそらくないと)全体にわたって取らないために2、プラス(V&1)
3は、比較関数は、構造体名電子、構造中に書かれています
見つけるのは難しい、コスト関数は本当に良い理想的な状態である(ターゲット状態にそれぞれ操作するように2つのノブが近い)が、達成することは現実には難しい、あなたには、いくつかのより正確な評価を行うことができます、と私は高-Vではありません1の係数(1.1、1.2、1.3)(これは高速であるため、1.3以下のコードを記述する)ことができますよりもわずかに大きく、デバッグを所有することができます
これは次のようになります。
ブール演算子<(constのE&A)のconst { +(AV >> 1)* 1.3 +(AV&1)としてリターンS +(V >> 1)* 1.3 +(V&1)>。 }
小さな変化が大幅にほとんど400msの(300ミリ秒より高速なデータポイントの最大値、高速で、効率を改善するとは限らない使用の巨大な男が、300ミリ秒まで)
完全なコード
#pragma GCCの最適化( "Ofast") の#include <ビット/ STDC ++ H> 名前空間STDを使用して、 #defineは現在[[P] [今[P]]]× 今の#define Y [P] INT TX、[13] [5]、[5] = {0、2、3、[30000000]をkは、4、1}。 構造体E { 今INT S、和、V、[13]、ステップ[20]。 ブール演算子<(constのE&A)のconst { +(AV >> 1)* 1.3 +(AV&1)としてリターンS +(V >> 1)* 1.3 +(V&1)>。 } インラインボイド変化(INT P){ X = [x]は、Xが= TXに、yは[Y]に=。 V + =(TX == 2)* 3 - (TX = 2!)+(Y == 2)* 3 - (Y = 2!)。 ステップ[++ S] = P、和+ =(TX == 1) - (TX == 2)+(Y == 1) - (Y == 2)。 } インラインINTのget(){ int型のTMP(0)。 (1 = I int型、iは= 12 <; ++ I)TMP =(TMP << 2)+今[I]。 TMPを返します。 } }トップ、TMP、T。 ボイドJust_Do_It(){ PRIORITY_QUEUE <E> Q。 q.push(トップ) (!q.empty())、一方{ TMP = q.top()。q.pop(); {(; I --I iは12 = INT)ため 、T = TMP。 t.change(I); IF(t.sum == 12){ のprintf( "%d個の\ n"、TS)。 以下のために(INT i = 1; iが= TSを<; ++ I)のprintf( "%dの"、t.step [I])。 返します。 } int型TT(t.get())。 続ける([TT]をK)であれば、 [TT]をK = 1。 q.push(T)。 } } } int型のmain(){ (I = 1 int型、iは<= 12; ++ i)について scanf関数( "%D%D%D%D%D"、&top.now [I]、および[I] [1]、および[I] [2]、および[I] [3]、および[I] [4])。 以下のために(i = 1からint型、iは= 12に<; ++ I) top.sum + =(top.now [I] == 1)、top.v + =(top.nowを[I] == 1)?0:5 - I; [top.getを()] K = 1。 早くやれよ (); 0を返します。 }