アルゴリズムのマジック定数

はじめに



現在、このようなコーディング標準(コーディング標準)の記述原則は、保守と開発を容易にするものとして広く知られています。 これらの原則は多くのソフトウェア会社で使用されており、開発ツールと静的コード分析により、さまざまな自動化が可能になります。 同時に、プログラミングのエンジニアリングタスクでは、「適切なコード」の概念を拡張する必要があります。 一見非常に特殊な例、つまりアルゴリズムで定数パラメーターを使用する練習を通して、「良い」エンジニアリングコードについて議論しようとします。



この記事は、特にキャリアを開始する際に、開発者の自己管理を強化するタスクを設定していることをすぐにお知らせしたいと思います。 以下に示すすべての例は、特定の計算問題や特定のアルゴリズムを参照せずに、モデルの状況と見なされる必要があります。 私たちの目標は、高品質のエンジニアリング/アルゴリズムプログラミングのパターンを定式化することです。



次のコードが目を痛めるかどうかを考えてみましょう。



if (abs(leftVoltage - rightVoltage - 150.7 * balanceCurrent) > 0.002) doSomethingImportant();
      
      





個人的に、それは私を非常に困難にします。 まず、150.7が何であるかは完全に不明です。

150.7は正確な抵抗の抵抗値であり、デバイスインスタンスごとに異なる可能性があり、実際にはキャリブレーションファイルから読み取る必要があります。 0.002とは何ですか? これは特別なコメントはありませんが、これは後で指定できる実験的なしきい値のようです。



最初の血



宇宙人銀河宇宙船のリベットの品質管理を自動化するタスクを提供されたジュニアプログラマーAlyoshaを想像してください。 これらのリベットはコンベアに到着し、デジタルカメラで撮影されます。 Alyoshaは、これらのリベットの写真を分析し、リベットの形状が規格に準拠しているかどうかを判断するコードを記述する必要があります。







上司を喜ばせるために、Alyoshaはリベットを推定するためのアルゴリズムをすぐに実装したとします。 このアルゴリズムは、テストセットから悪いリベットと良いリベットの画像を完全に分離し、問題は解決され、Alyoshaは別のプロジェクトに切り替えられました。



その後、次のことが起こりました。 リベットはもう少し進み、コンベアの速度が上がり、エンジニアのボリアはカメラのシャッター速度をわずかに短くしました。

同時に、カメラからの画像は少し暗くなりましたが、リベットはまだはっきりと見えていました。 同時に、Aleshinのアルゴリズムは、高品質のリベットを誤って拒否することがありました。 どうしたの?



させる I これはサイズの入力モノクロ画像です WI\回HI 座標付き x そして y 。 Alyoshaは、リベットがきしむ音に気づいた Z すべてのトレーニング画像で、しきい値フィルタリングを見つけることができました。



xy inZ LongleftrightarrowImin<Ixy<Imax







同時に、高品質のリベット Zgood エリアで見つけることができます:

Amin<Zgood<Amax







合計、Alyoshaは4つの経験定数を導入しました IminImaxAmin そして Amax 少なくとも1つ( Imin )カメラの再構成後に関連性が失われました。



少し経験を積んで、Alyoshaは次のことを行うことができました。必要な定数の値を構成ファイルに転送し、実際の計算方法でプロジェクトのドキュメントを補完します。 これは、単にコード内にこれらの値を非表示にするよりも優れていますが、Aleshinの同僚に、アルゴリズムを手動で設定する追加のタスクを任せます。 もちろん、そのような決定は満足のいくものとは言えませんが、特に難しい状況では存在する権利があります。



どのソリューションがより合理的でしょうか? 輝度と面積のバンドパスフィルターのパラメーターは、平均輝度と画像面積に対する相対値に変換できます。 例えば Amin に置き換えることができます Amin cdotWI cdotHI どこで Amin -また、経験的ですが、すでにより不変の値です。



次に宇宙船工場で何が起こったのかを推測してみましょう。

リベット除去の品質が不十分だったため、チーフテクノロジストのVitalyは、プログラミングの複雑さからはほど遠く、高感度で2倍の解像度を持つより高価なカメラを緊急に評価することにしました。 このようなチームワークの論理的な結果は、すべてのリベットのピクセル数が2倍になり、そのうちの1つがバンドパスフィルターを通過しなかったため、100%拒否されます。 有能なプロジェクト管理で節約できる可能性はありますが、今はそれについてではありません。



入力の正規化



入力データを均一な形式にすることで、定数の選択に関する多くの問題を回避できます。 画像-1つのヒストグラムフォーム、3Dモデル-1つの解像度など 多くの場合、そのような議論は正規化に反して進められ、初期情報の一部が失われることになります。 これは事実ですが、アルゴリズムのパラメーターを使用したさらなる作業の簡素化は、多くの場合、このマイナスを上回ります。



入力データの最大正規化の問題に関するまさにその声明により、開発者は、画像が90度回転するとどうなるかを考えることができますか? そして、サイズがインチで来るならば? そして、誰かが入力に、素材の細かい質感を伝える高解像度の3Dモデルを渡すとしたらどうでしょうか。



ただし、正規化を行う必要がない場合の素晴らしい例-写真の照明付きピクセル(ハイライト)の検索。 最大RGB輝度(255、255、255)のピクセルは、ズーム中にわずかにぼやけた細いストライプを形成する可能性があります。 同時に、照らされたピクセルの明るさは隣接するピクセルと平均化され、明るいピクセルと区別することはほとんど不可能になります。 したがって、画像からグレアを正確に選択してカットすることはできません。







校正定数



十分に低レベルのデータを処理する場合、古典的なキャリブレーションの問題が発生します。 これは、サーミスタの電圧から温度への変換、およびレーダー応答の観測対象の座標への変換です。 これらの変換はすべて、一定のパラメーターセットによって何らかの方法で決定され、これらのパラメーターを決定する手順はキャリブレーションと呼ばれます。



通常、校正パラメータは外部ソースから取得されます。 ひどい罪は、これらのパラメーターをハードコードすることです。 そのようなコードがコードレビューのためにすぐに除外されない場合、疑いの外のままで、ソフトウェア製品全体の動作を長期間損なう可能性があります。 システムは正確に動作しませんが、エラーメッセージがどこかに表示されることはほとんどありません。



ただし、図を完成させるには、観測値の内部依存性によりキャリブレーションパラメーターの計算が可能になる場合、自動キャリブレーションが可能な問題があることに注意する必要があります。 たとえば、 複数のビュージオメトリまたはMotionのキャリブレーションされていない構造の最新の章を参照してください。カメラのキャリブレーションパラメーターは、さまざまな角度の重複する画像のセットから決定されます。



総論



定数に意味のある名前を付け、その意味についてコメントしてください。 これは非常に脆弱なコードであり、言語やコンパイラの知恵を入力しても保護されないことに注意してください。



アルゴリズムのパラメーターを構造にグループ化します。 これにより、通常、コードの可読性が向上し、デバッグ中に重要なパラメーターを見逃すことがなくなります。



1つのパラメーターが他のパラメーターで表現されていることがわかっている場合は、この関係をコードに反映してください。 そうしないと、最善の意図を持った人が、最適ではないが一貫性のあるパラメーターを一貫性のないものに変更します。 たとえば、半径のある円を探しています R = 10および面積 S =314。これは、実際には1つのパラメーター(半径)があるため、良くありません。 R = 10、および S= piR2 。 2つのパラメーターを持つコードは、学校の数学を忘れたプログラマーによって簡単に破られる可能性があり、1つのパラメーターを持つコードはより信頼性が高く見えます。



アルゴリズムに非経験的定数が含まれていることがあります。 たとえば、分布の裾を評価する必要があります。 このような評価の正確さは、アルゴリズムの作成者の数学的準備によって大幅に決定されます。

評価定数は改善される場合がありますが、そのような改善は通常、孤立したタスクです。 他の開発者にとっては、この事実についてコメントすることが重要です。



まとめ



経験的定数はアルゴリズムコードの自然な部分ですが、開発者から細心の注意が必要です。 上記で説明した定数を使用するためのルールをもう一度リストします。



一般に、明日、高い確率で定数によって開発者に提示されるこれらのパラメータは、最適化の対象となる場合があります。

すべてのタイプのパラメーターを正しく入力すると、最適化手順の構築が大幅に簡素化されます。キャリブレーション定数と推定定数は最適化されず、経験的パラメーターのみが最適化されます。 このシンプルさが、エンジニアリングコードの品質の実用的な基準の1つとして役立つことを願っています。



All Articles