教えてください。
1.文字列の配列はどのように宣言すればよいのでしょうか?
char [3][3][20] = {{"朝","昼","晩"},{"morning","evening","night"},{"6:00","12:00","18:00"}};
これでできるとおもうのですが、もっと効率的な宣言ってあるのでしょうか?

2.また、この変数を3つのソースファイルで使用できるグローバル変数にしたいのですが、どのように宣言すればよいのでしょうか?
リンカエラー(外部シンボルが未解決)が発生してしまい、困っています。

def.h(ここで宣言したい)
 -----|----
 |   |   |
A.h  B.h C.h
 |   |   |
A.cpp B.cpp C.cpp

ちなみにBorland C++ Builder5を使っています。

このQ&Aに関連する最新のQ&A

A 回答 (3件)

> どのようにクラス化をすればよいか教えていただければ幸いです



あくまでも一例として読んで下さい。

「定義情報」のように、プログラムの中でインスタンスがひとつで良いものを実装する
やり方に Singleton パターンというのがあります。

例えば、こんな感じ。どんな定義情報か分からないんで、時刻情報を扱うクラスだと
思って名前をつけます。

◆ ヘッダ
class TimeRangeInfo {
private:
TimeRangeInfo();
static TimeRangeInfo* timerangeinfo_g;
public:
static TimeRangeInfo* Instance();
// 定義アクセス用のメソッド
const char* getLabel(int hour, int minute) const;
};

◆ソース
#include "timerangeinfo.h"

TimeRangeInfo* TimeRangeInfo::timerangeinfo_g = NULL;

TimeRangeInfo* TimeRangeInfo::Instance()
{
if (timerangeinfo_g == NULL) {
timerangeinfo_g = new TimeRangeInfo;
}
return timerangeinfo_g;
}

TimeRangeInfo::TimeRangeInfo()
{
// 定義の内容を自分のメンバーに登録する
}

const char* TimeRangeInfo::getLabel(int hour, int minute) const
{
// 自分で持っている定義情報から hour、minute にあたる情報を抜き出す
return 抜き出した値;
}

◆使う人
#include "timerangeinfo.h"

// 16:50 は、どんな区分か?
cout << TimeRangeInfo::Instance()->getLabel(16, 50) << endl;

という感じです。

# コンパイルなんかはしてないけど、勘弁 m(_ _)m

定義情報にアクセスするためのキーが何か存在するでしょうから、それを引数に
した情報取得用のメソッドを必要な分だけ作れば良い。

このクラス内部に、どのように定義情報を持つかは、外部には隠蔽されている
のだから、どんな風にやっても良いですね。例えば、外部変数とするにしても
static な(つまり、extern ではない)スコープにすれば、あまり影響は出ない
ですし。

◆ TimeRangeInfo クラスのソース
#include "timerangeinfo.h"

TimeRangeInfo* TimeRangeInfo::timerangeinfo_g = NULL;

static const char* data[100][256] = {
{"data-1", "data-2", ....
//延々とデータが続く

100×256 のデータのキーが何か想像がつかない(100種類のキーに対して、
データが 256 個もあるの?)のですが、私だったら、hash_map なんかを
使うかなあ。

# でも、TimeRangeInfo クラスの内部に隠蔽されているから、何を使っても
# 後で変更するのは簡単ですよね。
    • good
    • 0
この回答へのお礼

パソコンが調子悪く回答に送れて申し訳ありませんでした。
なるほど、いろいろ勉強になりました。
しかし、C++とはなんておくが深いものなのでしょう。
重ね重ね、ご丁寧にありがとうございました。

お礼日時:2001/10/24 19:02

> 2.また、この変数を3つのソースファイルで使用できるグローバル変数にしたい



グローバル変数にすること自体はお勧めできませんが、やり方だけ。

No.1 の回答でも問題はないんですが、A.cpp ~ C.cpp は、この時刻の定義を
使う、という意味で同じ位置付けですから、A.cpp だけ特別、ってのはあまり
良くないですね。

というわけで、グローバル変数の定義をするソースだけを作ってしまいましょう。

(例えば、)def.h は、

extern const char g_timerange[3][3][20];

def.cpp を作って、

#include "def.h"

const char g_timerange[3][3][20] = {{"朝","昼","晩"},{"morning","evening","night"},{"6:00","12:00","18:00"}};

A.cpp などでは、def.h をインクルードして使います。リンクの際には def.o も
リンクの対象にします。


質問の範囲を多少超えますが、どうしてもグローバル変数にするのであれば、

・値の定義として使うのだから、書き込みができないように const 宣言をつけよう
・名前の衝突を考えて、なるべくユニークになるように冗長度の高い変数名にしよう

というアドバイスを付け加えておきます。

後、蛇足をもうひとつ。

せっかく、C++ なんですから、文字列の配列にするよりも、「時間の定義を知っている
クラス」として実装する方が良い、と思いますよ。
    • good
    • 0
この回答へのお礼

a-kumaさん、いつも丁寧な回答ありがとうございます。
やっぱりグローバル変数は良くないのですね。それをクラス化ですか?
例では非常に少ない文字と量ですが作ろうとしているのは、[100][256][80]位の大きい文字配列です。
A.cpp,B.cpp,C.cppからそれぞれその文字データを取り出そうと考えているのですが、どのようにクラス化をすればよいか教えていただければ幸いです。
宜しくお願いします。

お礼日時:2001/10/11 13:23

1.


お書きになられたコードがもっとも効率的です。

2.
def.hで実体を宣言するのなら、A.cppだけで def.hをインクルードし、他のB.cpp, C.cppでは extern宣言をします。
extern char hoge[3][3][20];
    • good
    • 0
この回答へのお礼

早速の回答ありがとうございました。

お礼日時:2001/10/11 13:04

このQ&Aに関連する人気のQ&A

お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!

このQ&Aと関連する良く見られている質問

Qchar AA[]{"全角文字"};から"全"という一字を取り出したい

 今晩は、Cの初心者です、宜しくお願いします。
 全角文字の入ったchar AA[]{"全角文字"};から"全"という文字一字を取り出す時にAA[0]とかくとエラーになります。
 どのようにしたら取り出せるのでしょう。
 ポインタを使う方法と使わない方法を教えて下さい。
 宜しくお願いします。

Aベストアンサー

お疲れ様です。

まずお伺いしたのがOSおよび開発するためのコンパイラです。

ロケール等の話は分かりませんが、昔のC言語で日本語を扱う場合には全角文字1文字で2個つのchar領域を使用していました。
(マルチバイト文字セットと言います。)

詳細は参考URLを参照の事。

windowsでVCと仮定した場合、charを使われていると言うことは、多分、shift-jis(シフトJIS)で文字列を扱っていると思われます。

結論として全角文字1文字だけを取り出したいという場合は、結局char2個分のデータを取り出す必要があります。

>char AA[]={'全','角'};

char AA[]="全角";
とし
>printf("%s%s\n" , AA[0],AA[1] ) ;

printf("%c%c\n" , AA[0],AA[1] ) ;
とすれば、「全」だけを表示する事が可能と思われます。

日本語を文字列で表示する為の文字コードについては
Shift-JISだけでなく、UnicodeやUTF・EUC・JISなどがあります。

もう少し詳しく記載してあるホームページはないか探してみましたが、ちょっと無理でした。

参考URL:http://marupeke296.com/CPP_charUnicodeWideChar.html

お疲れ様です。

まずお伺いしたのがOSおよび開発するためのコンパイラです。

ロケール等の話は分かりませんが、昔のC言語で日本語を扱う場合には全角文字1文字で2個つのchar領域を使用していました。
(マルチバイト文字セットと言います。)

詳細は参考URLを参照の事。

windowsでVCと仮定した場合、charを使われていると言うことは、多分、shift-jis(シフトJIS)で文字列を扱っていると思われます。

結論として全角文字1文字だけを取り出したいという場合は、結局char2個分のデータを取り出...続きを読む

Qtry{}catch(){}とデストラクタの関係を教えてください。

try-catchでメモリ確保を含むクラスをスローした場合、デストラクタはどの時点で働くのか、教えてください。たとえば、↓の使いかたは大丈夫でしょうか?

【1】
try{
 throw(CError(100, "エラー情報"));
}catch(CError& err){
 //ここでerrを参照しても問題ないのでしょうか?
}

【2】
try{
 CError err(100, "エラー情報");
 throw(err); // (1)
}catch(CError& err){
 //ここでerrを参照しても問題ないのでしょうか?
 //まだデストラクタはちゃんと動作するのでしょうか?
 //catchが呼び出し元のメンバであったりしても大丈夫なのでしょうか?
}

宜しくお願いします。

Aベストアンサー

【1】【2】どちらの場合も問題がありません。
コンパイラが必要に応じてerrオブジェクトのコピーを作成します。
デストラクタが呼び出されるタイミングはコンパイラに依存するところもあると思いますが、
例えばVC7.1では【2】は以下のように動作します。
(1) errオブジェクトのコンストラクタが呼び出される
(2) CErrorクラスのテンポラリオブジェクト(以下a)のコピーコンストラクタが呼び出される。
(3) errオブジェクトのデストラクタが呼び出される
(4) catch文まで到達
(5) aオブジェクトのデストラクタが呼び出される。

VC7.1では、【1】は以下のように動作します。
(1) errオブジェクトのコンストラクタが呼び出される
(2) catch文まで到達
(3) errオブジェクトのデストラクタが呼び出される。

コンパイラがオブジェクトのコピーを省略しているようです。

Q[VC++][MFC][SDI]ダイアログコントロールもしくわツールバー!!詰まってます!!

現在VC++6.0でMFCを使いSDIのプログラムを作っているのですが、フォームにダイアログバーを張っています。

これをツールバーのように自由に動かしたり、左右上下にドッキングさせたり。
これって実現可能でしょうか?

色々ためしてみたんですが無理でした。
やっぱ不可能ですかね?

これが無理なんであればデフォルトで作成されるツールバー([新規作成][開く][保存]等が入ってる)にコントロール(ボタンやリストボックス)を追加して使用、と考えているのですがこれも難しい!!!


まだまだ未熟者なのですがどうかご存知の方おられましたらご教授ください!!
よろしくお願いします!!

Aベストアンサー

Dannerです。
参考URL(英語)を載せておきます。

参考URL:http://www.codeguru.com/Cpp/controls/toolbar/placingcontrolsintoolbars/article.php/c2505/

Qmain関数のとる引数(argc , *argv[])の意味について

 今日は、Cの初心者です宜しくお願いします。
 
 main関数(main(int argc , *argv[]))のとる引数、argcのCと*argv[]のVはどのような意味の略なのでしょうか、
なにか意味があるようなきがするのですが。
 宜しくお願いします。

Aベストアンサー

文字列の個数(argument count)

"ARGument Vector" の略という説と、"ARGument Value" の略という説がある。

Q{} の名称、使い方

初心者です。教えて頂けますか?

int main ()
{
int a;
a = 9;
{
int b;
b = a;
}
return 0;
}
のような使い方を見たのですが
見やすくする為でしょうか?
調べていのですが名称を教えて頂けますか?
よろしくお願いします

Aベストアンサー

{} という記号の名称でしょうか。
それとも、 { ~ } を利用した手法の名称でしょうか。

{} は英名ではブレース(brace)といいます。
日本語名では中括弧とか波括弧と呼ばれています。

http://ja.wikipedia.org/wiki/%E6%8B%AC%E5%BC%A7#.E6.B3.A2.E6.8B.AC.E5.BC.A7.EF.BD.9B.EF.BD.9D

C系の言語の影響を受けたプログラミング言語においてはブロックや
スコープの範囲を指定するのによく利用されます。
Perlではハッシュ(連想配列)の要素指定にも使われます。


このカテゴリの人気Q&Aランキング

おすすめ情報