2

ファイルが JPEG か PNG かをテストする必要がありますが、ファイル拡張子が間違っている可能性があるため、信頼できません。これを実現するために、GIL を使用することにしました。

宣言 (および定義) するヘッダー ファイルを次に示しboost::gil::png_read_dimensionsます。boost::gil::png_read_dimensions 「場所が有効なPNGファイルに対応していない場合、std::ios_base::failureをスローします」と明確に述べています。実際、これは関数の実際の動作と同等のようです。

問題は、ここでboost::gil::jpeg_read_dimensions見ることができるものです。また、 「場所が有効な JPEG ファイルに対応していない場合、std::ios_base::failure をスローする」ことも明確に述べています。しかし、そうではないようです!例外はスローされず、代わりに stdout または stderr に出力され、プログラムが終了します。libjpeg

次のコードを参照してください。

#include <iostream>
#include <string>

#include <boost/gil/extension/io/jpeg_io.hpp>
#include <boost/gil/extension/io/png_io.hpp>

using std::cout;
using std::cerr;
using std::endl;
using std::string;
using std::ios_base;

namespace bg = boost::gil;

int main(int, char**) {
  const string not_jpeg_or_png ("image.gif");

  cout << "bg::png_read_dimensions:" << endl;
  try {
    bg::png_read_dimensions(not_jpeg_or_png);
  } catch(const ios_base::failure &ib_f) {
    cerr << "what: " << ib_f.what() << endl;
  }

  cout << "\nbg::jpeg_read_dimensions:" << endl;
  try {
    bg::jpeg_read_dimensions(not_jpeg_or_png);
  } catch(const ios_base::failure &ib_f) {
    cerr << "what: " << ib_f.what() << endl;
  }

  cout << "\nDone." << endl;

  return 0;
}

プログラム出力:

bg::png_read_dimensions:
what: png_check_validity: invalid png file: unspecified iostream_category error

bg::jpeg_read_dimensions:
Not a JPEG file: starts with 0x62 0x6c

what: ... yadiyadiyada ...Done.が印刷されていないことに注意してください。

例外が見過ごされずに成功しないようにする} catch(...) {代わりに、試してみました。} catch(const ios_base::failure &ib_f) {例外はスローされません。

ここで本当に明らかな何かが欠けていますか...?私は何か間違ったことをしていますか?回避策はありますか?

4

2 に答える 2

1

最も簡単な方法は、ファイルの最初の数ビットを読み取り、それらがファイル タイプのシグネチャと一致するかどうかを確認することです。

89 50 4E 47 0D 0A 1A 0A => PNG

FF D8 FF => JPEG

于 2015-05-15T18:19:27.653 に答える
0

スローされた例外が明らかにキャッチできない理由がわかりません。バグかもしれません。

ただし、私が提案するタスクを達成するには

  • libmagicまた
  • identify(ImageMagick より)

これは、他の答えが示唆することを行います。

この回答には、libmagic の使用方法の例が含まれています (通常は Linux に存在しますが、他のプラットフォームでビルドして (静的に) リンクすることができます)。

于 2015-05-15T17:49:45.320 に答える