0

だから私はこれを見つけました:

std::fill_n(array, 100, value);

しかし、それは私が探しているものではないかもしれないと思います。私は appay *pointer を持っていて、それらがピクセルであり、それらがたくさんあるため、いくつかの連続した要素に同じ値をすばやく入れる必要があります。

だから私は使用します:

*(pointer)=*(pointer+1)=value;

(pointer)= (pointer+1)=*(pointer+2)=value;の場合も あります。しかし、最初のケースが最も重要です。追加の "+" は問題ではありませんが、SDL の関数を使用して画面の黒 (またはその他) を塗りつぶすと、高速に動作し、どのように最適化されているかわかりません。

したがって、配列のいくつかの隣接要素に同じ値を入力する必要がある場合、いくつかのクールなトリックがあります。

たぶん、(Uint64) と <<32 にキャストして、2 つの同じ値を 2 つの整数のトリックに配置しますか?

わかりました、申し訳ありませんが、最初からこれが何のためにあるのかを説明していませんでした。そのため、ボクセル オブジェクトをレンダリングすると、オブジェクトの外側のレイヤーのみを描画するため、回転後にオブジェクト内の画面にピクセルが表示されないスポットが表示されることがあります。そして、基本的にオブジェクトを1ピクセル右に伸ばすことでスムージングを行いたいと思います。だから私はピクセルを置いている間、私は彼のようなものを彼の右側に置く必要があります.

4

2 に答える 2

1

100 個 (または 1000 個)unsigned intの要素を埋めたい場合は、必要な方法を選択できます。それは、それであれstd::fill_nforループであれ、数が非常に少ないため、この操作を頻繁に行っても違いがわかりません。

ただし、より大きな配列の値を設定する場合、たとえば、4 つの符号なしカラー コンポーネントで構成されるピクセルを含む 8k x 8k テクスチャの場合は、使用できる方法を簡単に比較できます。

#include <iostream>
#include <ctime>
#include <cstdint>

int main(){
    long unsigned const size = 8192 * 8192 * 4;
    unsigned* arr = new unsigned[size];

    clock_t t1 = clock();
    memset(arr, 0, size*sizeof(unsigned));

    clock_t t2 = clock();
    std::fill_n(arr, size, 123);

    clock_t t3 = clock();
    for(int i = 0; i < size; ++i)
        *(arr + i) = 123;

    clock_t t4 = clock();
    int64_t val = 123;
    val = val << 32 | 132;
    for(int i = 0; i < size / 2; ++i)
        *(int64_t*)(arr + i * 2) = val;

    clock_t t5 = clock();

    std::cout << "memset = " << t2 - t1 << std::endl;
    std::cout << "std::fill_n = " << t3 - t2 << std::endl;
    std::cout << "for 32 = " << t4 - t3 << std::endl;
    std::cout << "for 64 = " << t5 - t4 << std::endl;

    delete arr;

    return 0;
}

1.memset

この関数は、他の方法と比較して、配列をゼロにする速度を示すためだけにここで使用されています。これは最速の解決策ですが、すべてのバイトを同じ値に設定したい場合にのみ使用できます(特にあなたのケースでは便利だ00xFF思います)。

2. 32 ビット値std::fill_nでループするfor

std::fill_nソリューションの中で最も遅いように見え、32 ビット値のソリューションよりもわずかに遅くなります。for

3. for64 ビット SYSTEM での 64 ビット値によるループ

この競争に勝ったので、これがあなたが選ぶことができる解決策だと思います. ただし、マシンが 32 ビットの場合、プロセッサは 1 つの 64 ビット値を 2 つの 32 ビット値として処理するため、結果は 32 ビット値のループに匹敵すると予想されます (コンパイラとプロセッサによって異なります)。値。

于 2013-07-27T08:19:29.950 に答える
0

はい、1 つの 64 ビット変数を使用して、値を 2 つ (またはそれ以上) の 32 ビット (またはそれ以下) の連続する要素に入れることができます。多くの場合があります。明らかに、64 ビットのプラットフォームを使用する必要があり、プラットフォームがアライメントをどのように処理するかを知っておく必要があります。

このようなもの:

uint32_t  val = ...;
uint64_t  val2 = val;
(val2  <<= 32) |= val;

for (uint32_t* p = ...; ...)
     *(uint64_t*) p = val2;

SSE を使用する場合は、同様の手法を使用するとより効果的です。

于 2013-07-27T07:20:49.700 に答える