2012-01-03 17 views
3

私は既存の1Dアレイを持っています、memsetそれをゼロにする最速の方法ですか?既存の配列をゼロにする最速の方法は何ですか?

+0

関連:http://stackoverflow.com/questions/8528590/what-is-the-advantage-of-using-memset-in-c – Mysticial

+1

はい、これまでのところ最速です。 mem ...すべての人は、目的地の単語だけでなく目的地のバイトを設定する方法を理解しているので、高速です。つまり、例えば4バイトのゼロバイトがメモリワードに移動される場合、memsetはメモリロケーションをすべて1つにクリアします。ボーナスとして、memsetとmemmoveとmemcopyは移植可能です。 –

+0

'memset'はすべてのビットを0に設定しますが、それはいつも起こっているとは限りません。あなたは移植性に気をつけますか?配列には何が入っていますか? –

答えて

4

最速...おそらくはい。 バギーはほぼ確実です!

多くの場合、実装、プラットフォーム、および配列の種類によって異なります。

C++では、変数が定義されるとそのコンストラクタが呼び出されます。配列が定義されると、配列のすべての要素のコンストラクタが呼び出されます。

アレイタイプがすべてゼロで表現できる初期状態を持つことがわかっていて、既定のコンストラクタが何も実行しない場合にのみ、メモリを消去することは「良好」とみなすことができます。

これは一般にです。組み込み型の場合は、他の型の場合はfalseです。

最も安全な方法は、デフォルトの初期化された一時的な要素を割り当てることです。 Tがcharある場合、関数はインスタンス化memsetとおりに変換し、

template<class T, size_t N> 
void reset(T* v) 
{ 
    for(size_t i=0; i<N; ++i) 
     v[i] = T(); 
} 

注意。だから、同じスピードで、それ以上のスピードはありません。

+0

プラットフォーム:Windows、タイプ:float、サイズ:1e6。また、ランタイムスピードが最優先事項であり、安全性よりも重要です。 – Shibli

+1

@ Shilbli:上記のテンプレートでも良いです:memsetはバイトを設定します。私の関数は、プロセッサワードと同じサイズの浮動小数点数を設定します。コンパイラが最適な最適化を持っている場合(レジスタにペースiを入れ、外部ループ定数としてT()を保持する)は、特殊化されていないmemsetよりも高速です。 しかし、それはほとんどがライブラリではなくコンパイラに依存しています。 –

+0

これは、標準ライブラリで 'std :: fill_n'を使って行うことができます。 – Blastfurnace

3

実装固有のため、これはわかりません。しかし、一般的には、memsetが最も速くなります。なぜなら、ライブラリの実装者は、非常に高速化するために多くの時間を費やしています。そして、コンパイラは、を知っているため、手作業では実行できない最適化を行うことができます。memsetを意味します。

+1

サポートされている場合は、組み込み関数については言及しません。 –

+0

非常に大きな配列の場合、ターゲットマシンのストレージ管理機能を利用して、 'calloc'が高速になることがあります。しかし、厄介な内部を掘り下げることなく知る方法はありません。 –

+0

@HotLicks彼は "既存の配列"と言っていた –

関連する問題