Upload
yasuhiro-yoshimura
View
5.839
Download
1
Embed Size (px)
DESCRIPTION
【関東GPGPU勉強会#3】OpenCVの新機能 UMatを先取りしよう
Citation preview
OpenCVの新機能 UMatを先取りしよう
関東GPGPU勉強会#3 2013/11/30
@dandelion1124
自己紹介(1/3)
Twitter:@dandelion1124
• 学生時代は画像処理の研究に従事。
• 現在は都内勤務エンジニア。
• 研究室でOpenCVのTipsサイトを作っていたらOpenCV関連書籍を
書くことになり今に至る。
blog: http://www.atinfinity.info/blog/
wiki: http://www.atinfinity.info/wiki/
自己紹介(2/3)
• 書籍執筆 – OpenCVプログラミングブック
• 和訳本(原稿チェック) – 詳解 OpenCV – 実践 コンピュータビジョン
• 雑誌関連 – 日経ソフトウェア(2011年3月号) 特集記事担当
自己紹介(3/3)
• メインで活動している勉強会
–関東コンピュータビジョン勉強会 #cvsaisentan
http://sites.google.com/site/cvsaisentan/
本日のアジェンダ
• OpenCVとは?
• 前置き
• OpenCVのデータ構造
• UMatとは?
• サンプルコード
• UMatを使うには
• UMatのTips
本日のメイン
本題に入る前の前準備
OpenCVとは?
Intelが開発・公開したOpen SourceのComputer Vision
ライブラリ。現在はWillow Garageが開発を行っている。
http://opencv.org/
• 公式サポートOS
– Windows/Linux/Mac OS/Android/iOS
• 公式サポート言語
– C/C++/Python/Java
※有志による非公式ラッパーは以下のサイトにまとめています。
http://www.atinfinity.info/wiki/index.php?OpenCV%2FOpenCV%20wrapper%20list
前置き
ある日OpenCV MeetingNotesで以下の記載を見かける
– 3.0 will do a lot more work on this. But OpenCL will vanish and be put into automatic acceleration in the other modules • It will accelerate automatically if you use "umat" (Universal Matrix).
• Tests often show 10 to 100x acceleration on GPU
– If user casts to umat and pass to functions, it will use GPU acceleration if available achieving the speedup. • Data is not copied in conversion back and forth between mat and
umat. Use mat if you want pixel access.
http://code.opencv.org/projects/opencv/wiki/2013#2013-11-05 から抜粋
前置き
ある日OpenCV MeetingNotesで以下の記載を見かける
– 3.0 will do a lot more work on this. But OpenCL will vanish and be put into automatic acceleration in the other modules • It will accelerate automatically if you use "umat" (Universal Matrix).
• Tests often show 10 to 100x acceleration on GPU
– If user casts to umat and pass to functions, it will use GPU acceleration if available achieving the speedup. • Data is not copied in conversion back and forth between mat and
umat. Use mat if you want pixel access.
http://code.opencv.org/projects/opencv/wiki/2013#2013-11-05 から抜粋
なんか凄そう! (小並感)
前置き
という残念な理由からUMatについて説明することに
しました。
ただし、あくまでOpenCV 3.0で入る予定の機能なので、正式な
導入時は本発表時と内容が変わっている可能性がある点
ご了承ください。
前置き
というか、そもそも、最新コード(https://github.com/Itseez/opencv/)に
UMat実装されているんでしょうか?
前置き
というか、そもそも、最新コード(https://github.com/Itseez/opencv/)に
UMat実装されているんでしょうか?
あった!
modules/core/src/umatrix.cpp
前置き
じゃあ、開発版ドキュメント読んでみようかな? http://docs.opencv.org/trunk/modules/core/doc/core.html
前置き
じゃあ、開発版ドキュメント読んでみようかな? http://docs.opencv.org/trunk/modules/core/doc/core.html
「UMatのドキュメントはまだ無い」
(※2013/11/29時点)
ご清聴ありがとうございました
前置き
ドキュメントが無いので、しぶしぶソースを
読んで使い方を調べることにしました。
というわけで、本編に戻ります。
OpenCVの画像データ構造
OpenCVで画像を格納するために使うデータ構造は
おおまかに以下の4つ。
• cv::Mat 画像データの入れ物(CPU版)
• gpu::GpuMat 画像データの入れ物(CUDA版)
• ocl::oclMat 画像データの入れ物(OpenCL版)
• cv::UMat 画像データの入れ物(CPU/OpenCL版)
OpenCVの画像データ構造
OpenCVで画像を格納するために使うデータ構造は
おおまかに以下の4つ。
• cv::Mat 画像データの入れ物(CPU版)
• gpu::GpuMat 画像データの入れ物(CUDA版)
• ocl::oclMat 画像データの入れ物(OpenCL版)
• cv::UMat 画像データの入れ物(CPU/OpenCL版)
oclMatについては前回勉強会の発表資料を参照ください。
http://www.slideshare.net/YasuhiroYoshimura/gpgpu2opencvopencloclmat
※上記資料は2013年6月時点のものなので最新版ではAPI仕様が少し変わっています。
OpenCVの画像データ構造
OpenCVで画像を格納するために使うデータ構造は
おおまかに以下の4つ。
• cv::Mat 画像データの入れ物(CPU版)
• gpu::GpuMat 画像データの入れ物(CUDA版)
• ocl::oclMat 画像データの入れ物(OpenCL版)
• cv::UMat 画像データの入れ物(CPU/OpenCL版)
今日のお話はこの部分がメイン
UMatとは?
• Mat/oclMat間の差異を隠蔽したデータ構造
• UMatに画像データを入れて画像処理の関数を実行すると、OpenCLが使える環境なら自動でOpenCL実装を使ってくれる
• UMatを使って実装しておけばCPU/OpenCLのコードを共通化できる
UMatとは?
• Mat/oclMat間の差異を隠蔽したデータ構造
• UMatに画像データを入れて画像処理の関数を実行すると、OpenCLが使える環境なら自動でOpenCL実装を使ってくれる
• UMatを使って実装しておけばCPU/OpenCLのコードを共通化できる
UMatとは?
UMatに画像データを格納
OpenCLが使える 実行環境?
oclMatの実装を使う Matの実装を使う
OpenCVの画像処理関数をコール OpenCV内部で
勝手にやってくれる
Yes
No
UMatとは?
• Mat/oclMat間の差異を隠蔽したデータ構造
• UMatに画像データを入れて画像処理の関数を実行すると、OpenCLが使える環境なら自動でOpenCL実装を使ってくれる
• UMatを使って実装しておけばCPU/OpenCLのコードを共通化できる
サンプルコード(グレースケール化) #include <opencv2/core/core.hpp>
#include <opencv2/imgproc/imgproc.hpp>
#include <opencv2/highgui.hpp>
using namespace cv;
int main(int argc, char** argv)
{
Mat src = imread(“lena.jpg ", IMREAD_UNCHANGED);
Mat dst;
cvtColor(src, dst, COLOR_BGR2GRAY);
imwrite (“lena_gray.jpg", dst);
return 0;
}
#include <opencv2/core/core.hpp>
#include <opencv2/imgproc/imgproc.hpp>
#include <opencv2/highgui.hpp>
#include <opencv2/ocl/ocl.hpp>
using namespace cv;
int main(int argc, char** argv)
{
Mat src = imread(“lena.jpg ", IMREAD_UNCHANGED);
Mat dst;
ocl::oclMat oclsrc (src );
ocl::oclMat ocldst;
ocl::cvtColor(oclsrc, ocldst, COLOR_BGR2GRAY);
ocldst.download(dst);
imwrite (“lena_gray.jpg", dst);
return 0;
}
Mat(CPU版)のコード oclMat(OpenCL版)のコード
点線で囲った部分が共通化できていないコード部分
サンプルコード(グレースケール化) #include <opencv2/core/core.hpp>
#include <opencv2/imgproc/imgproc.hpp>
#include <opencv2/highgui.hpp>
#include <opencv2/ocl/ocl.hpp>
using namespace cv;
int main(int argc, char** argv)
{
Mat src = imread(“lena.jpg ", IMREAD_UNCHANGED);
UMat usrc = src.getUMat(ACCESS_READ);
UMat udst;
cvtColor(usrc, udst, COLOR_BGR2GRAY);
imwrite (“lena_gray.jpg", udst);
return 0;
}
UMat(CPU/OpenCL版)のコード
UMatを使って実装するとCPU/OpenCLのコードを共通化できる!
UMatのサンプルコードを使って 各処理をもう少し詳しく説明します
サンプルコード(グレースケール化) #include <opencv2/core/core.hpp>
#include <opencv2/imgproc/imgproc.hpp>
#include <opencv2/highgui.hpp>
#include <opencv2/ocl/ocl.hpp>
using namespace cv;
int main(int argc, char** argv)
{
Mat src = imread(“lena.jpg ", IMREAD_UNCHANGED);
UMat usrc = src.getUMat(ACCESS_READ);
UMat udst;
cvtColor(usrc, udst, COLOR_BGR2GRAY);
imwrite (“lena_gray.jpg", udst);
return 0;
}
グレースケール化
①ヘッダ読み込み
③UMat初期化
②画像読み込み
④画像処理
⑤画像書き込み
サンプルコード(グレースケール化) #include <opencv2/core/core.hpp>
#include <opencv2/imgproc/imgproc.hpp>
#include <opencv2/highgui.hpp>
#include <opencv2/ocl/ocl.hpp>
using namespace cv;
int main(int argc, char** argv)
{
Mat src = imread(“lena.jpg ", IMREAD_UNCHANGED);
UMat usrc = src.getUMat(ACCESS_READ);
UMat udst;
cvtColor(usrc, udst, COLOR_BGR2GRAY);
imwrite (“lena_gray.jpg", udst);
return 0;
}
③UMat初期化
②画像読み込み
④画像処理
⑤画像書き込み
UMatを使うにはocl.hppの インクルードが必要
①ヘッダ読み込み
OpenCVのヘッダをインクルード
サンプルコード(グレースケール化) #include <opencv2/core/core.hpp>
#include <opencv2/imgproc/imgproc.hpp>
#include <opencv2/highgui.hpp>
#include <opencv2/ocl/ocl.hpp>
using namespace cv;
int main(int argc, char** argv)
{
Mat src = imread(“lena.jpg ", IMREAD_UNCHANGED);
UMat usrc = src.getUMat(ACCESS_READ);
UMat udst;
cvtColor(usrc, udst, COLOR_BGR2GRAY);
imwrite (“lena_gray.jpg", udst);
return 0;
}
③UMat初期化
④画像処理
⑤画像書き込み
画像ファイルを読みこんで Mat形式で格納する。
②画像読み込み
サンプルコード(グレースケール化) #include <opencv2/core/core.hpp>
#include <opencv2/imgproc/imgproc.hpp>
#include <opencv2/highgui.hpp>
#include <opencv2/ocl/ocl.hpp>
using namespace cv;
int main(int argc, char** argv)
{
Mat src = imread(“lena.jpg ", IMREAD_UNCHANGED);
UMat usrc = src.getUMat(ACCESS_READ);
UMat udst;
cvtColor(usrc, udst, COLOR_BGR2GRAY);
imwrite (“lena_gray.jpg", udst);
return 0;
}
④画像処理
⑤画像書き込み
srcに入れたデータをもとに UMatのインスタンスを作る
③UMat初期化
サンプルコード(グレースケール化) #include <opencv2/core/core.hpp>
#include <opencv2/imgproc/imgproc.hpp>
#include <opencv2/highgui.hpp>
#include <opencv2/ocl/ocl.hpp>
using namespace cv;
int main(int argc, char** argv)
{
Mat src = imread(“lena.jpg ", IMREAD_UNCHANGED);
UMat usrc = src.getUMat(ACCESS_READ);
UMat udst;
cvtColor(usrc, udst, COLOR_BGR2GRAY);
imwrite (“lena_gray.jpg", udst);
return 0;
}
⑤画像書き込み グレースケール化する
④画像処理
サンプルコード(グレースケール化) #include <opencv2/core/core.hpp>
#include <opencv2/imgproc/imgproc.hpp>
#include <opencv2/highgui.hpp>
#include <opencv2/ocl/ocl.hpp>
using namespace cv;
int main(int argc, char** argv)
{
Mat src = imread(“lena.jpg ", IMREAD_UNCHANGED);
UMat usrc = src.getUMat(ACCESS_READ);
UMat udst;
cvtColor(usrc, udst, COLOR_BGR2GRAY);
imwrite (“lena_gray.jpg", udst);
return 0;
}
⑤画像書き込み
グレースケール化した画像を ファイルに書き込む
UMatを使うには
■CMake CMakeで以下の手順を行うことで ソリューションファイルが生成される ①「WITH_OPENCL」にチェックを入れる ②「Configure」ボタンを押す ③「Generate」ボタンを押す
④生成されたソリューションを使ってOpenCVのライブラリを生成
■OpenCL環境導入 PCにOpenCLのSDKをインストールして おく必要がある
■開発版OpenCVコード入手 2.4.xにはUMat実装が入っていないのでgit or githubから開発版のコードを取得する必要があります https://github.com/Itseez/opencv/
UMatのTips
• 今の実行環境でOpenCL環境が使えるかどうかを調べるユーティリティ関数があります
– ocl::haveOpenCL()
• UMatの処理でOpenCL実装を使うかを知るためのユーティリティ関数があります
– ocl::useOpenCL()
ただし、#include <opencv2/core/ocl.hpp> を追加する必要あり!
UMatのTips
• ユーザによってはUMatの処理で勝手にOpenCL側の処理に入って欲しくない場合もあるのでは?
– ocl::setUseOpenCL関数にtrue/falseを指定することでUMatでOpenCLを使う/使わないを決められます。
ただし、#include <opencv2/core/ocl.hpp> を追加する必要あり!
まとめ
• OpenCV 3.0あたりからUMatというデータ構造が追加される予定
• UMatを使うとCPU/OpenCLの実装コードを共通化できる
• UMatを使った実装を行うとき、CPUモードでアルゴリズムを検証してから、OpenCLモードに切り替えるのも容易そう
• 「UMatのドキュメントはまだ無い」(※2013/11/29時点)
• 正式発表を楽しみに待ちましょう!
おわり