C++ プログラムで scanf() を使用すると、cin を使用するよりも高速ですか?

以下は、単純なケースの簡単なテストです:標準入力から数値のリストを読み取り、すべての数値を XOR するプログラムです。

iostream バージョン:

#include <iostream>

int main(int argc, char **argv) {

  int parity = 0;
  int x;

  while (std::cin >> x)
    parity ^= x;
  std::cout << parity << std::endl;

  return 0;
}

scanf バージョン:

#include <stdio.h>

int main(int argc, char **argv) {

  int parity = 0;
  int x;

  while (1 == scanf("%d", &x))
    parity ^= x;
  printf("%d\n", parity);

  return 0;
}

結果

3 番目のプログラムを使用して、33,280,276 個の乱数を含むテキスト ファイルを生成しました。実行時間は次のとおりです:

iostream version:  24.3 seconds
scanf version:      6.4 seconds

コンパイラの最適化設定を変更しても、結果はあまり変わらないようです。

したがって、実際には速度に違いがあります。

編集: ユーザー clyfish は、速度の違いは主に C I/O 関数との同期を維持する iostream I/O 関数によるものであると指摘しています。 std::ios::sync_with_stdio(false); を呼び出すことでこれをオフにすることができます :

#include <iostream>

int main(int argc, char **argv) {

  int parity = 0;
  int x;

  std::ios::sync_with_stdio(false);

  while (std::cin >> x)
    parity ^= x;
  std::cout << parity << std::endl;

  return 0;
}

新しい結果:

iostream version:                       21.9 seconds
scanf version:                           6.8 seconds
iostream with sync_with_stdio(false):    5.5 seconds

C++ iostream が勝利! この内部同期/フラッシュが、通常 iostream i/o を遅くする原因であることが判明しました。 stdio と iostream を混在させていない場合は、それをオフにできます。そうすれば、iostream が最速になります。

コード:https://gist.github.com/3845568


http://www.quora.com/Is-cin-cout-slower-than-scanf-printf/answer/Aditya-Vishwakarma

cin のパフォーマンス /cout 基礎となる C ライブラリとの同期を維持する必要があるため、遅くなる可能性があります。これは、C IO と C++ IO の両方を使用する場合に不可欠です。

ただし、C++ IO のみを使用する場合は、IO 操作の前に以下の行を使用してください。

std::ios::sync_with_stdio(false);

詳細については、対応する libstdc++ ドキュメントを参照してください。


おそらく scanf は、ストリームを使用するよりもいくらか高速です。ストリームは多くのタイプ セーフを提供し、実行時にフォーマット文字列を解析する必要はありませんが、通常は過剰なメモリ割り当てを必要としないという利点があります (これはコンパイラとランタイムによって異なります)。とはいえ、パフォーマンスが唯一の最終目標であり、クリティカル パスにいる場合を除き、より安全な (遅い) メソッドを本当に優先する必要があります。

sscanf のような文字列フォーマッタのパフォーマンスについて詳しく説明している、Herb Sutter による「The String Formatters of Manor Farm」という非常に興味深い記事があります。 と lexical_cast そして、どのようなものがそれらを遅くまたは速く走らせていたのか.これは、おそらく C スタイルの IO と C++ スタイルの間でパフォーマンスに影響を与える種類のものと似ています。フォーマッタとの主な違いは、型の安全性とメモリ割り当ての数です。