2017-09-19 6 views
0

、このテストコード:stdoutでフリーになっているファイルを書き込む方が速いのはなぜですか? Windows上で実行すると

  • write with freopen clocks elapsed: 2767
  • write with fopen clocks elapsed: 8337

理由:

#define _CRT_SECURE_NO_WARNINGS 
#include <stdio.h> 
#include <time.h> 
#include <assert.h> 

int main() { 
    // The clock() function returns an approximation of processor time used by the program. 
    // The value returned is the CPU time used so far as a clock_t; 
    // to get the number of seconds used, divide by CLOCKS_PER_SEC. 
    auto buf = new char[1048576]; // 1MB 
    auto cache = new char[512 * 1024]; 

    // initialize the buffer 
    for (int i = 0; i < 1048576; ++i) 
     buf[i] = i; 

    auto fp_reopen = freopen("data_freopen.bin", "wb", stdout); 
    assert(fp_reopen != nullptr); 
    setvbuf(fp_reopen, cache, _IOLBF, 512 * 1024); 
    auto clock_begin = clock(); 
    for (int i = 0; i < 1000; ++i) { 
     auto n = fwrite(buf, 1048576, 1, fp_reopen); 
     assert(n == 1); 
    } 
    fflush(fp_reopen); 
    auto clock_end = clock(); 

#ifdef _WIN32 
    freopen("CONOUT$", "w", stdout); 
#else 
    freopen("/dev/tty", "w", stdout); 
#endif 

    printf("write with freopen clocks elapsed: %zu\n", clock_end - clock_begin); 

    auto fp = fopen("data_fopen.bin", "wb"); 
    assert(fp != nullptr); 
    setvbuf(fp, cache, _IOLBF, 512 * 1024); 
    clock_begin = clock(); 
    for (int i = 0; i < 1000; ++i) { 
     auto n = fwrite(buf, 1048576, 1, fp); 
     assert(n == 1); 
    } 
    fflush(fp); 
    clock_end = clock(); 
    fclose(fp); 

    printf("write with fopen clocks elapsed: %zu\n", clock_end - clock_begin); 
    delete[] buf; 
    delete[] cache; 
    getchar(); 
} 

は、これらの結果を生成しますか?

+0

コードをオフサイトではなく、質問の一部として含めてください。スタックオーバーフローを理解しておく必要はありません。 – Chris

+3

2つのテストを入れ替えてもう一度やり直してください。 –

+0

@Chrisこのことについて申し訳ありません。携帯電話で質問を編集しました。あなたのリマインダーと助けてくれてありがとう! – vertextao

答えて

2

あなたの質問は面白いですが、非常にシステム固有:

  • Linux上のgccとglibcで、私が打ち鳴らすと、アップルのlibcで、OS/Xの両方で動作し
  • のために非常に類似したタイミングを取得しますfopenのタイミングは、一貫してfreopenよりも少し速いようです。
  • getchar()への最終呼び出しが示唆するように、あなたはWindows上でテストを実行しています...残念ながら、このシステムを試してみることはできません。

マイクロソフトではランタイムライブラリで変わったことが起こっている可能性がありますが、実際には2つの別々の1GBファイルの作成をベンチマークしている可能性が高くなります。ファイルシステムの状態、キャッシュ、またはその他のOS固有の原因により、2番目のファイルが最初のファイルよりも作成に時間がかかる可能性があります。この潜在的な副作用は、各ファイルを閉じた後に削除するか、別の順序でテストを実行してみてください。

+0

はい、あなたは正しいです。テストの順序を変更すると、結果が逆転します。 * 'fopenクロック経過時に書き込み:2346' *' freopenクロック経過時に書き込み:8088' – vertextao

関連する問題