ホーム » 2010 » 6月 (ページ 3)

月別アーカイブ: 6月 2010

2010年6月
 12345
6789101112
13141516171819
20212223242526
27282930  

検索・リンク

bit演算と情報量の計算

テスト前の最後ということで、プログラミングの基礎としての基本計算機能としての、 bit演算子の説明と、数値の意味を理解するための情報量の計算について説明した。

bit演算子

bit演算子としては、&(AND),|(OR),^(EXOR),~(NOT)の説明を行い、 以下のようなプログラムも交え論理演算子との違いも強調する。

printf( "%d" , 3 && 5 ) ; // 0以外が表示
printf( "%d" , 3 & 5 ) ; // 0011 and 0101 = 0001

これに加え、<< , >> といったビットシフト演算子を示したり、 bit演算子による負数などを説明する。

printf( "%d" , (~3)+1 ) ; // -3が表示。bit反転+1=2の補数

情報量

確率の逆数の和といった説明は5年の授業に残しておいて、 0~255の256通りは、8bitで覚えることができる…といった説明から、 R,G,B各色256諧調の640x480dotの画面を覚えるのに、どれだけのメモリが必要か? とか、 0~65535の音の大きさ、ステレオで、サンプリングレート44.1KHz、74分のデータを 覚えるために、どの程度のメモリが必要か?

ネタとして、74分の理由を説明したけど、Webを調べると色々な説が紹介されている。 ググったトップのネタだと、 CDの規格を決めた人が規格を正当性を主張するためにハッタリでカラヤンの名前を出したという記事が… ということで、諸説はっきりしないみたいだな…

電子情報Webサーバ、SSLに対応

学術研究機関を対象とした無償のSSLキー発行サービスを利用して、 学科WebサーバをSSL対応にしました。 先日より学内での動作を確認し、本日より高専FireWall部の、 内向けProxyサーバでも同様の鍵の登録を行い、 SSL(https)での接続ができるようになりました。

このBLOGのようなメンテナンスの学外からの操作や、 学科メールサーバの学外からの操作の時に、 オレオレ認証キー信用するの?」の警告無しで、 安心して使えるようになりました。

第21回高専プロコン応募(校内審査)

今年度のプロコンのテーマが発表され、 創造工学およびIT研究会より応募があり、 学内審査の結果、以下の5チームを書類審査に応募することになりました。

  1. 課題:「ブレイン・スペース~新感覚電脳補完~」(4EI:小林貴、3EI多田)
  2. 課題:「Thlowで行こう!」(4EI:川口、片岡、出口、月田、中川、笠嶋)
  3. 自由:「貼ろうわーるど~地球を創って転がそう~」(4EI:飯田、井上、島田、関、山下)
  4. 自由:「砂であそぼう!!~砂で描くメッセージ~」(4EI:本山、久世、小林成、森、ツェンデ )
  5. 競技:「4セルくれ~2セルで十分ですよ~」(4EI:戸嶋、直江、八田、原、山田)

UPKIオープンドメイン証明のProxyへの登録

先日、UPKIオープンドメイン証明の鍵作成や、登録作業を行ったが、 最終段階として、学科WebサーバはFireWallの内側で、カギは 内向けProxyについても登録の必要があった。 内部的に動作の確認の後の運用開始の必要性があり、 内部的に動作確認が取れた。 最終的に情報処理センターにて、作業が行われたみたいで、 この学科サーバも、https接続で「オレオレ証明書、信じる?」的な、 警告が出ていたけれど、無事、警告無しで接続できることが確認できた。 めでたし、めでたし….

2010年6月6日(第167回)

特別企画 ザ・ルーズドックスの永田さん、古市さんが出演!!
 学生時代の思い出を中心に、たーっぷりお話いただきました。(収録)

photo100606.jpg
収録後、番組に対するメッセージをもらいました!!

リスト構造の導入

mallocによる動的メモリ確保の説明が終わったので、 次のステップとしてリスト構造の話を行う。 アパートの回覧板の管理をイメージしてもらいながら、 次のデータの場所を管理する方法を説明。

int top = 3 ;
struct List {
int  data ;
int  next ;
} list[ 10 ] = {
{ 5 , 4 } , //0
{ 4 , 0 } , //1
{ 2 , 1 } , //2
{ 1 , 2 } , // 3
{ 8 ,-1 } , //4
} ;
for( int i = top ; i >= 0 ; i = list[ i ].next )
printf( "%d" , list[ i ].data ) ; // 昇順に表示される。

次に、この次のデータの「配列添え字」ではなく、 データ1件毎にメモリを確保し、次のメモリの番地をつなぐために、 以下のような方法をとる。

struct List {
int  data ;
struct List* next ;
} ;
// 理解してもらうためにあえて面倒な処理をそのまま書く
struct List* top ;
top = (struct List*)malloc( sizeof( struct List ) ) ;
top->data = 1 ;
top->next = (struct List*)malloc( sizeof( struct List ) ) ;
top->next->data = 2 ;
top->next->next = (struct List*)malloc( sizeof( struct List ) ) ;
top->next->next->data = 3 ;
top->next->next->next = NULL ;
// もう少し簡単に
struct List* cons( int x , struct List*n ) {
struct List* ans ;
if ( (ans = (struct List*)malloc(sizeof(struct List))) != NULL ) {
ans->data = x ;
ans->next = n ;
}
return ans ;
}
struct List* top = cons( 1 , cons( 2 , cons( 3 , NULL ) ) ) ;

この例で、データがいかに作られるのか説明の後、そのデータを扱うプログラムとして、 リストの件数・合計・最大値を求めるプログラムを、考えてもらったり、再帰呼び出しで 書いてもらう。

// 例:リストの件数
int count( struct List*p ) {
for( int c = 0 ; p != NULL ; p = p->next )
c++ ;
return c ;
}
// ループを使わずに再帰で合計
int sum( struct List*p ) {
if ( p == NULL )
return 0 ;
else
return p->data + sum( p->next ) ;
}

授業後にテストの質問として、過去問題の質問に答える。 昨年度の出題のネタだけど、ポインタと動的確保したデータのイメージを 確認する出題をしているが、詳しく授業でまだ説明していない。 来週は、テスト前対策ということで、説明を加えようか…

// 以下のようなメモリ確保を行った場合の、データの格納イメージは?
struct Complex {
double re , im ;
} ;
struct Complex data1[ 2 ] ;
struct Complex* data2
= (struct Complex*)malloc( sizeof( struct Complex ) * 2 ) ;
struct Complex* data3[ 2 ] = {
(struct Complex*)malloc( sizeof( struct Complex ) ) ,
(struct Complex*)malloc( sizeof( struct Complex ) ) ,
} ;
struct Complex** data4 ;
= (struct Complex**)malloc( sizeof( struct Complex* ) * 2 ) ;
data4[0] = (struct Complex*)malloc( sizeof( struct Complex ) ) ;
data4[1] = (struct Complex*)malloc( sizeof( struct Complex ) ) ;

高等専門学校機関別認証評価の説明会参加

高専や大学では、学校運営の適切さを評価するための機構として、 認証評価というシステムがあり、5年周期で大学評価学位授与機構によるチェックを受ける。 本高専では、前回の受審から5年ということで、平成24年に2回目の審査の予定となっている。

前回の審査では、JABEE委員・認証評価委員ということで、受審の資料作りに参加していたことから、次回審査で経験を活かすという意味で、再び認証評価委員となる予定…(T_T; ということで、 説明会に参加した。東京で6/1(火)13:00-17:00の説明会で、他の5名の方と「東京日帰り出張」という、 ハードスケジュールにて、説明を聞いてきた。 説明は、以下の5テーマで行われた。

  1. 高等専門学校機関別認証評価について
  2. 評価基準の資料作成にあたっての留意事項
  3. 教育の質の保証にあたっての資料
  4. 自己評価の方法などについて
  5. 申請手続きの流れ

という感じで説明を受けた。特に前回受審との違いについての変わった点では、 現状実施のエビデンスでは不足していると思われる点がいくつか見受けられた。 特に、説明者が何度も繰り返し説明していた点は、 高専の目的として、『使命・基本方針・達成目標』について明記して、この点を満たしていることを示す客観的なエビデンスが必要という点であった。

どちらにしろ、エビデンス作りなどでは全学的な取り組みも必要だし、 他の先生への説明という点で、みんなそろって 「配布のパワポ資料レジメの電子データを配布して欲しい…」 との感想で終わりました。

ファーストクラス客も100円寿司に行ってこい

ANAの目玉サービス、クレーム殺到で中止との記事をみかけた。 飛行機のファーストクラス・ビジネスクラスの座席で、 食事や飲み物などのサービスをタッチパネルでオーダーできるシステムを導入したけど、 操作をすぐに理解した人はいいけど、操作に慣れない人はサービスの悪循環で、 オーダーが出てくるまで待たされすぎてクレーム多発の末、 お金をかけたサービスだけど中止となったらしい。

最初は、タッチパネルの『ユーザインタフェースプログラムが悪いんじゃ?』とも思ったが、 記事によると使いこなす人はさっさと注文している様子。 となると、タッチパネルオーダに慣れない人種の問題にも思えてくる。

ということで、私なりの結論: 金持ちだからって高いすし屋に行くばっかりじゃなくって、 100円の回るすし屋の、タッチパネルオーダに慣れてから飛行機に乗れってことですね。

継承と仮想関数

先週は、派生・継承について説明を行ったが、今日はその続き。

void main() {
Person saitoh( "saitoh" , 45 ) ;
Jyoshi ashida( "ashida" , 60 ) ;
ashida.buka( &saitoh ) ;
Person* list[2] ;
list[0] = &saitoh ;
list[1] = &ashida ;
for( int i = 0 ; i < 2 ; i++ )
list[ i ]->print() ;
}

この例では、list[1]=&ashida ができることが注目点。 派生クラスのポインタは、基底クラスのポインタに格下げが許される。 この例であれば、list[1]->print() では、list[1]=&ashida とする時点で、 Jyoshi型がPerson型になっているため、Person型のprint()が実行され、 部下の情報は表示されない。

しかし、実際のプログラムでは、list[1]->print() にて、Jyoshi::print() が呼び出して 欲しい場合も多い。こういった場合には、仮想関数を用いる。 virtual 宣言されたメソッドが宣言されると、データ構造の構築時に、 型情報を覚えるためのID(型情報)も保存される。 また、仮想関数の呼び出しでは、型情報に応じてメソッドが呼び出される。

class Person {
:
public:
virtual void print() {
printf( "%s %d\n" , name , age ) ;
}
} ;
class Jyoshi : public Person {
private:
int size ;
Person* table[ 5 ] ;
public:
virtual void print() {
Person::print() ;
for( int i = 0 ; i < size ; i++ )
table[i]->print() ;
}
} ;

パソコンでプログラムを打ち込みながら、受講している人がいたので、 Person型のサイズsizeof( Person )を確認すると、 virtual 宣言した場合、データサイズが4byte拡大することが確認できた。 実際には、型情報として「仮想関数の関数ポインタ配列へのポインタ」が 使われることが多いので、そのポインタ分の4byte増加と思われる。

int main(int argc,char**argv)

Cの授業でも、間違いとは説明するものの"void main(){}" でプログラムを書いていたり するけれど、C++だと明確にエラーになるため、argc,argvも含めて解説する。

int main( int argc , char*argv[] ) {
for( int i = 0 ; i < argc ; i++ )
printf( "%s\n" , argv[i] ) ;
// プログラムを a.out Hello World と実行すれば、
// argv[0]=a.out,argv[1]=Hello,argv[2]=World になる。
return 0 ; // mainの正常終了(プロセスのリターン値でOSに渡される)
}

new delete

上記の仮想関数のプログラム例は、実プログラムでは、 以下のようなコードでインスタンスを生成する場合も多い。

Person *saitoh = new Person( "斉藤" , 45 ) ;

と簡単に説明しようとしたら、new,delete の説明をしてなかった。 new, delete は動的にメモリを確保するC言語のmalloc,freeに相当する演算子。

// C言語の場合
int *p ;
if ( (p = (int*)malloc( sizeof(int) * 100 ) != NULL ) {
// p[i] を整数配列として使える
free( p ) ;
}
// C++のnew,deleteの場合
int *p = new int[ 100 ] ;
// new演算子はメモリ確保の失敗には例外を使うので
// NULLチェックは不要。
// p[i]を整数配列として使える
delete [] p ;
// Personの例で説明
Person* p = new Person( "斉藤" , 45 ) ;
// new Personでは、コンストラクタも実行される。
p->print() ;
delete p ;
// delete では、デストラクタ呼び出しも行われる。

システム

最新の投稿(電子情報)

アーカイブ

カテゴリー