• 検索結果がありません。

Microsoft PowerPoint - ep_cpp04.ppt

N/A
N/A
Protected

Academic year: 2021

シェア "Microsoft PowerPoint - ep_cpp04.ppt"

Copied!
11
0
0

読み込み中.... (全文を見る)

全文

(1)

C++による

画像処理プログラミング

-第4回-情報科学研究科

視覚情報メディア講座

佐藤 智和 tomoka-s@is.naist.jp

version 1.0

(2)

今回説明すること

|

前回の課題の解答

|

バグを防ぐためのC++の記述方法

z

const

(3)

課題1の解答例

unsigned char getRGBIntensity::CRGBimage( int x, int y, int color_offset ) {

return image_data[(x+y*width)*3+color_offset];

}

void setRGBIntensity::CRGBimage( int x, int y, int color_offset, int v ) {

image_data[(x+y*width)*3+color_offset]=v;

}

void copyPixel::CRGBimage_operator( Cimage *input, Cimage *output, int from_x, int from_y, int to_x, int to_y )

{

output->setIntensity(to_x, to_y, 0, input->getIntensity( from_x, from_y, 0 ) );

output->setIntensity(to_x, to_y, 1, input->getIntensity( from_x, from_y, 1 ) );

output->setIntensity(to_x, to_y, 2, input->getIntensity( from_x, from_y, 2 ) );

}

(4)

課題2の解答例

int main() {

//クラスのポインタを定義

CRGBimage *input_image, *mosaic_image, *mosaic_resized, *mirror_image, *resize_image, *trimm_image; //画像処理用クラスを定義 CRGBimage_operator image_operator; //入力画像用のクラスの実体を作成 input_image=new CRGBimage(); //画像を読み込み input_image->loadImage( "./test.ppm" ); //画像出力用のクラスの実体を作成 resize_image=new CRGBimage(); mosaic_image=new CRGBimage(); mosaic_resized=new CRGBimage(); mirror_image=new CRGBimage(); trimm_image=new CRGBimage(); //各種画像処理の実行

image_operator.resize( input_image, resize_image, 0.1 ); image_operator.mosaic( input_image, mosaic_image, 10 ); image_operator.resize( mosaic_image, mosaic_resized, 0.5 ); image_operator.horizonalMirror( resize_image, mirror_image );

image_operator.trimming( input_image, trimm_image, 280, 350, 410, 450 ); //画像の保存 resize_image->saveImage( "./resize.ppm" ); mosaic_resized->saveImage( "./mosaic.ppm" ); mirror_image->saveImage( "./mirror.ppm" ); trimm_image->saveImage( "./trimming.ppm" ); //作成したクラスの実体を破棄

delete input_image; delete resize_image; delete mosaic_image; delete mosaic_resized; delete mirror_image; delete trimm_image; return 0;

(5)

const について

const とは、関数の引数の前につける修飾子で、その引数が関数内で変更

されない(できない)ことを保障する

//コンソールにテキストを出力する関数

void print_text(

const

char *string ) {

//コンソールにテキストを出力

cout << string;

//配列を改変しようとする悪いコード

string[0]=0;

}

//メイン関数

int main() {

char *test=“It is test.”;

print_text( test );

print_text( test );

}

(6)

他関数へのconst変数の引渡し

//別の関数

void test_func( char *test ) {

test[0]=0; //testの中身を改変

}

//コンソールにテキストを出力する関数

void print_text(

const

char *string ) {

//コンソールにテキストを出力

cout << string;

test_func( string );

}

ここでコンパイルエラーとなるため

char *temp;

temp=strdup( string );

test_func( temp );

free( temp );

等とするか、test_funcの引数に

constを付ける必要がある

特定の関数でconstを引数の修飾子として記述した場合には、その関数内でconst

でない型に変換することはできず、const引数をとらない関数にデータをそのまま渡す

ことはできない。

(7)

クラスにおけるconst

//画像オペレータクラス(グレースケール用) class Cimage_operator {

virtual void copyPixel( const Cimage *input, Cimage *output, int from_x, int from_y, int to_x, int to_y ){ output->setIntensity(to_x, to_y, input->getIntensity( from_x, from_y ) );

} public:

void resize( const Cimage *input, Cimage *output, int new_width, int new_height ); void resize( Cimage *input, Cimage *output, float scale );

void horizonalMirror( Cimage *input, Cimage *output )

void trimming( Cimage *input, Cimage *output, int left, int top, int right, int bottom ); void mosaic( Cimage *input, Cimage *output, int scale );

};

クラスのメンバ関数がメンバ変数を変更しないことを保障するためにconstを付ける

ただし、関数内でクラスのポインタから呼ばれるメンバ関数getIntensityが、メンバ変数を

書き換えないことを保障するために、getIntensityの定義も以下のように変更する必要が

ある。

unsigned char Cimage::getIntensity( int x, int y )

const

{

return image_data[x+y*width];

}

(8)

メモリリークを防ぐテクニック

メモリリークとは?

-c++では new, deleteを多様するが、deleteを忘れるとメモリが開放されず、

最終的にはメモリが確保できない状態になり異常終了する

//コンソールにテキストを出力する関数

void image_test() {

Cimage *input, *output;

Cimage_operator op;

input = new Cimage();

input –> load( “./test.ppm” );

output = new Cimage();

op.resize( input, output, 0.5 );

delete input;

}

//メイン関数

int main() {

for (i=0 ; i<1000 ; i++ )

image_test();

}

delete outputを忘れている

ため、test.ppmの画像サイズ

分のメモリ領域が開放されない

(9)

メモリリークを防ぐテクニック

クラスの解放忘れのチェック

-コンストラクタ、デストラクタにグローバルなカウンタをつけるだけで、

プログラム中で何回メモリ開放忘れが発生したか確認できる。

int number_of_cimage_instance=0; //カウンタをグローバル変数として作成 class Cimage { public:

Cimage() : width(0), height(0), image_data(NULL), max_intensity(255) {

number_of_cimage_instance++;

}

~Cimage( ){

number_of_cimage_instance--;

}

static void printUndeletedInstances() {

cout<< number_of_cimage_instance << “instances are still remained.” << endl; } }

クラスのインスタンス無しに呼ばれるメンバ関数にはstaticをつけておく

int main() { //各処理の最後に以下の構文でチェック関数を呼ぶ Cimage::printUndeletedInstances(); return 0; }

(10)

メモリリークを防ぐテクニック

malloc解放忘れのチェック

-malloc, freeをカプセル化するクラスCmemoryを自作する

class Cmemory { int counter; public: Cmemory() : counter(0) {} ~Cimage(){}

void *_malloc( int size, char *source_file, int line ) { counter++;

return malloc( size ); }

void _free( void *buffer ) { counter--; free( buffer ); } }

確保したアドレスの情報や、呼び出し元のファイル名(__FILE__), ライン(__LINE__)等

を引数にし、リスト化して保存しておけば、どこで確保したものが開放されていないかま

で特定できる。また、既に開放ずみのものを再度開放していないかどうか確認すること

も拡張次第で可能となる。

Cmemoryクラスの基本構造の例

(11)

前回の課題

提出者リスト

551203 651001 651002 651004 651005 651010 651011

651013 651014 651023 651027 651028 651029 651031

651034 651040 651043 651044 651045 651048 651050

651051 651052 651055 651057 651063 651065 651068

651074 651077 651080 651084 651085 651087 651089

651090 651100 651105 651108 651123 651125 651128

651135 651138 651145

提出したのに自分の学籍番号がない人は連絡してください。

以上45名

参照

関連したドキュメント

The goods and/or their replicas, the technology and/or software found in this catalog are subject to complementary export regulations by Foreign Exchange and Foreign Trade Law

READ UNCOMMITTED 発生する 発生する 発生する 発生する 指定してもREAD COMMITEDで動作 READ COMMITTED 発生しない 発生する 発生する 発生する デフォルト.

図 キハダマグロのサプライ・チェーン:東インドネシアの漁村からアメリカ市場へ (資料)筆者調査にもとづき作成 The Yellowfin Tuna Supply Chain: From Fishing Villages in

・大都市に近接する立地特性から、高い県外就業者の割合。(県内2 県内2 県内2/ 県内2 / / /3、県外 3、県外 3、県外 3、県外1/3 1/3

口腔の持つ,種々の働き ( 機能)が障害された場 合,これらの働きがより健全に機能するよう手当

※立入検査等はなし 自治事務 販売業

Fig.5 The number of pulses of time series for 77 hours in each season in summer, spring and winter finally obtained by using the present image analysis... Fig.6 The number of pulses

ダウンロードしたファイルを 解凍して自動作成ツール (StartPro2018.exe) を起動します。.