#pragma twice

KAB-studio > プログラミング > #pragma twice > 045 Version 3.20 CString とストリングテーブル

#pragma twice 045 Version 3.20 CString とストリングテーブル

前のページへ 表紙・目次へ 次のページへ

 Version 3.20
CString とストリングテーブル

さて、前回はレジストリについて見てみました
レジストリにー、数字いれてー、取り出したんだよねー
その辺を書き出すと……

// CCalcApp::InitInstance() の中。
    SetRegistryKey( "KamichanFactory" );
    dlg.m_iAns = GetProfileInt( "CalcDialog", "Ans", 0 );
    int nResponse = dlg.DoModal();
    if (nResponse == IDOK)
    {
        WriteProfileInt( "CalcDialog", "Ans", dlg.m_iAns );
    }

となります
あれ、質問! SetRegistryKey() って WriteProfileInt() の前にもあっ
たと思うんだけど
 CWinApp::SetRegistryKey() でセットしたキーはちゃんと保存されてる
から、 CWinApp::WriteProfileInt() を呼んだときもちゃんと効いてるんで

つまり、最初に一度だけ呼んじゃえばいいってことね
そゆこと
もひとつ、 TODO のコメントのとこって消しちゃっていいの?
いいんじゃないかな。あのコメントの意味は分かるでしょ?
うん、 OK ボタンを押したら、戻り値がどーたらこーたらして、この中
カッコの中に入るってことだもんね、まー分かっちゃえばなくてもいっか
それじゃあ、今日の本題。もしうっかり

        WriteProfileInt( "CalcDialog", "Ams", dlg.m_iAns );

なんてなったらどうしましょう
……どっか違うの?
 "Ams" になってるでしょ!
あ、ホントだ
こういうミスは、プログラムが大きくなればなるほど多くなるし、見つけ
るのも大変
というわけで?
今回は、このまえ見た〈ストリングテーブル〉の使い方について見てみま
しょう
あ、あれを使うんだ!
まずは CWinApp::SetRegistryKey() のから。リソースビューからストリ
ングテーブルを開いて
はーい。ワークスペースの ResourceView の String Table をダブルクリ
ック! はい開いたよー、あ、前の〈バージョン情報じゃ!〉のままだ
直しておいた方がいいかも……。で、 IDS_ABOUTBOX の下に点線で囲んで
るのがあるでしょ。それを
ダブルクリック! あ、プロパティ出た
まず【 ID 】から。今回は IDS_REG_COMPANY にしましょう
その意味は?
 ID で String で Registry で会社名だから
まんまねー
だからこーゆーのはまんまの方がいいんだって
そっか。で、キャプションは?
【キャプション】は KamichanFactory だってば
 SetRegistryKey() に渡すのなんだもんね
そういうこと。そしたらプログラムに戻って
えーっ!!
なんやねその非難ごーごーは
言ってみただけ。やっぱ SetRegistryKey() まわり書き換えるの?
そういうこと。 SetRegistryKey() の行と、その前2行を……

    CString cCompanyStr;
    cCompanyStr.LoadString( IDS_REG_COMPANY );
    SetRegistryKey( cCompanyStr );

って感じに書き換えて
……やっぱむずかしーね
だから〈えーっ!!〉?
分かる人にはこの苦労分かんないわよっ!
……〈君は労せず理解できたんだよね〉って思われるのはやだな
うっ
はっきり言うよ。火美ちゃんは僕の100分の1の労力でマスターできる
はず!
ってそれ自慢してない?
かもね。じゃ、プログラム見ていきましょう。1行目は?
んー、 CString って前に見たよね、確か文字とか使うためのクラス
そうそう。頭文字が C でしょ、これは MFC のクラスのあかし
あ、 CDialog とか CWinApp とかもそうだもんね
 CString も MFC のクラスのひとつ、文字列を操作するためのクラス。1
行目はこの CString 型の変数を作ってます
変数を作る、っていうのがクラスには必ず必要なんだね
そういうこと。クラスは鋳型、変数は実物。文字列を格納するためには、
変数として作らなきゃいけないわけ
それが cCompanyStr なんだ。で、2行目は、 CString::LoadString() っ
てメンバ関数を使ってるんだよね。レッツMSDN!
 LoadString をダブルクリックし F1 キーを押す。【該当するトピック】
ダイアログが表示される。
あ、 API にも LoadString() ってあるんだ
ストリングテーブルはウィンドウズのものだから、 MFC 使わなくてもも
ちろん操作できるわけ。でも
 CString 使った方が楽ってことねー。んじゃ CString::LoadString() を
ダブルクリック
 MSDNの CString::LoadString() のページが開く。
なんか簡素。あ、使用例がある! でもなんか複雑?
エラー処理はあとに回して、引数は?
えーっと、文字列リソースの ID だって。文字列リソースってストリング
テーブルのこと?
そう。ってことは?
 ID ってことはさっきの……あ、だから IDS_REG_COMPANY なんだ
【解説】に書いてあるとおり、この ID で指定した文字列をさっき作った
cCompanyStr の中に書き込みます
ここに書いてある〈オブジェクト〉って?
これは〈変数〉って読み替えていいかな。ホントはもっと広い意味なんだ
けど
広いって?
たとえば、ウィンドウズ上のウィンドウとかも〈オブジェクト〉のひとつ
ウィンドウってことは HWND の変数のこと?
ううん、ウィンドウズの中に、ウィンドウの情報が入ってるの。それがオ
ブジェクト。 HWND はそのオブジェクトを操作するためのものってことだね
なんかむつかしいかも……
確かにね。ま、今のところは変数ってことで
はーい。で、 cCompanyStr に IDS_REG_COMPANY にあたる文字列が入るか
ら、それを SetRegistryKey() に渡してるってことねー3行目
そういうこと。んじゃチェックしてみて
はーい。ビルドして実行! あ、答にさっきの数字が入ってる。ってこと
はちゃんと会社名があってるってことだよね
あってるってこと。こういうチェックをちゃんとすることが大切だから
はーい。で、他のもするの?
もちろん。自分でしてみて
う”、難しそう……
こういうのは聞くだけじゃなくて、ちゃんと自分で試すことが大事
分かってますよーだ。えーっと、まずストリングテーブルを開いて……
……と、皆さんには答を見てもらいましょう。まずストリングテーブルは、
こんな感じになります

IDS_REG_COMPANY    KamichanFactory
IDS_REG_DIALOG     CalcDialog
IDS_REG_ANS        Ans

そーいえば【値】ってどーでもいーの?
どうでもいいの。大事なのは IDS_REG_COMPANY とかの文字列の方だから
はーい
で、プログラムの方は

// CCalcApp::InitInstance() の中。
    CString cCompanyStr;
    cCompanyStr.LoadString( IDS_REG_COMPANY );
    CString cDialogStr;
    cDialogStr.LoadString( IDS_REG_DIALOG );
    CString cAnsStr;
    cAnsStr.LoadString( IDS_REG_ANS );

    SetRegistryKey( cCompanyStr );
    dlg.m_iAns = GetProfileInt( cDialogStr, cAnsStr, 0 );
    int nResponse = dlg.DoModal();
    if (nResponse == IDOK)
    {
        WriteProfileInt( cDialogStr, cAnsStr, dlg.m_iAns );
    }

うん、変数名違っちゃったけど、だいたい同じかな
ま、本当はもーっとシンプルにしたいんだけど、今の知識だとこれが限界
かな
シンプルって?
たとえば、今の状態だと cDialogStr と cAnsStr を逆に渡したりしかね
ないからね
そういうのも考えなきゃいけないんだ……。そういえばさ、こうやってす
れば、最初言ってた "Ams" な間違いってなくなるの?
もちろん。たとえば cAnsStr を cAmsStr にしたら……
あ、ビルドしたらエラーになっちゃった
 cAmsStr なんて変数作ってないからね。同じく IDS_REG_ANS を 
IDS_REG_AMS にしても
エラー。ストリングテーブルに IDS_REG_AMS なんてないもんね
こうすることで、ミスの起きやすさを大幅に減らせた
けど限界はある、と
そういうこと。それにね、色々問題もあってね
どゆこと?
火美ちゃんから見て、この新しいプログラムと古い方のと、どっちが分か
りやすい?
そりゃ前のでしょ。レジストリのキーにする文をそのまま渡してるんだか

そうなんだよね。安全策を採ろうとすると、どうしても【距離が離れる】
ことになるから
どゆこと?
上の例だと、文字列をストリングテーブルに置いて、 CString を間に挟
んだことで安全性を増したわけ。つまり安全性を上げるためには
間に何か入れなきゃいけないってことね。つまりアレみたいなもん?
……まあそうだけど……
そうなの?
つ、つまり、距離を置いたおかげで安全性は増したけど、プログラムとし
ては、 cCompanyStr には IDS_REG_COMPANY が入ってる、 IDS_REG_COMPANY
はストリングテーブルの KamichanFactory って追って見る必要があるわけ
じゃーアレとは違うじゃん
うー、まあそうだねぇ
ようするにさ、プログラムが見にくくなるってこと?
そういうことになるかな。直感的じゃなくなるんだね
あー、じゃあアレと同じかも
と、とにかくっ、こういうデメリットはあるけど、プログラムの安全性を
考えても、ストリングテーブルを使って処理しましょうってことで
みんなも使ってねー

/*
    Preview Next Story!
*/
……
ほらそんな怒んないで。アメあげる
アメ?
ほら
……
というわけで次回
< Version 3.21 イベントハンドラ >
につづく!!
元気になった?
……
 
del.icio.us 登録する
Yahoo!ブックマーク 詳細を表示 users
livedoorクリップ 詳細を表示 livedoorクリップ ブックマーク数
はてなブックマーク 詳細を表示 はてなブックマーク ブックマーク数
RSSに登録
del.icio.us 登録する
Yahoo!ブックマーク 詳細を表示 users
livedoorクリップ 詳細を表示 livedoorクリップ ブックマーク数
はてなブックマーク 詳細を表示 はてなブックマーク ブックマーク数
 
このページは、Visual C++ 6.0を用いた C++ 言語プログラミングの解説を行う#pragma twiceの一コンテンツです。
詳しい説明は#pragma twiceのトップページをご覧ください。