トップページ⇒tech
1001コメント300KB

C++相談室 part9

■ このスレッドは過去ログ倉庫に格納されています
0001デフォルトの名無しさんNGNG
現在最高のプログラム言語と言われるC++についてのご相談承ります。
(´∀`).。o(関連URLは>>2-5の辺り)
0449デフォルトの名無しさんNGNG
>>448
なにがいいたいの?
0450デフォルトの名無しさんNGNG
>>449
ポインタはC++ではアドレスなのか。そうでないのか。
規格書の記述ではわかりづらいが前者のようだということ。
0451デフォルトの名無しさんNGNG
>>450
それが重要なの?
0452デフォルトの名無しさんNGNG
>>451
一応ね。人にポインタを説明する時に頻出事項だし。
ぜひ確認しておきたいことではあるね。

ただし、一般にアセンブラなどで使ってる「アドレス」とは
異なる意味でのアドレスだということは確かだな。
ポインタの値はimplementation-definedだとはっきり書いてあるし。
0453デフォルトの名無しさんNGNG
>>450と>>452が矛盾してやしない?
0454デフォルトの名無しさんNGNG
>>453
いや、そう思いやすいかもしれないけど、そうではないと思う。
implementation-definedでかつアドレスなんだと思う。
勝手に処理系がつけた値を「アドレス」と呼んでしまえば、矛盾しない。
言葉の定義の問題だけど。
0455デフォルトの名無しさんNGNG
>>454
implementation-defined は、ようはどう定義しても間違いではないって
意味でしょ?例えば「aが整数だ」というルールがあったときに、
あんたはa=0だと主張しているに過ぎないんじゃない?
0456デフォルトの名無しさんNGNG
>>455
だから、もしも0という言葉が整数全体を表す言葉にも使える
ものだったとしたら(実際は違うけど)OKだよな?

あと、いくらimplementation-defined だと言っても
全く自由というわけではないぞ。当然他の規則と矛盾しない
ようにしなくてはならない。
0457デフォルトの名無しさんNGNG
仮定法過去だね。
0458デフォルトの名無しさんNGNG
>>457
そうだが。
いろいろな記述を見るに、アドレスはポインタだと考えないとつじつまが合わない。
決定的なのはさっきのallocation functionの記述。
それから、constやvolatileに関してはアドレスがポインタだと明記してある。
例えば、allocation functionの説明でもアドレスはポインタだとして
解説してるようだが、それ以外にもconstやvolatileに関してはアドレスが
ポインタだとはっきり明記してある。
この場合は確実にimplementation-definedで、かつアドレスなんだよ。
0459デフォルトの名無しさんNGNG
ん?なんか二度同じことを説明してしまった。スマソ。
0460デフォルトの名無しさんNGNG
>>448
本当に規格書読んだ?
ISO/IEC 14882:1998(E)
5.3.1
2
The result of unary & operator is a pointer to its operand.
0461デフォルトの名無しさんNGNG
>>460
ん?その部分は勿論読んだぞ。
「&はポインタを返す」だろ。
でも、ポインタがアドレスとはその部分だけでは断定できまい。
「&がアドレスを返す」と書いてない以上。
まあ、&は「address-of operator」って名前らしいが…

しかし、それ以外のいろんな記述を見るに、アドレスがポインタらしいと
いうのが俺の意見。
0462460NGNG
アドレスとポインタを混同してたわ。
046311NGNG
>constやvolatile(のT型)に関してはアドレスがポインタ
なだけでその他はそうであるとは限らない。ということだと思いまっせ。
0464デフォルトの名無しさんNGNG
>>463
文脈から見るに、その部分は「〜へのポインタ」という言い方をconstなど
に適用するとどうなるかを説明した文であって、そこだけアドレスがポインタ
だということを説明した文じゃないと思うわけよ。
それに、何度も言ってるように、他でアドレスとポインタを混同したような文がいくつもある。
比較的証拠っぽいのは14.3.2のプログラムのコメントとか、thisポインタが
アドレスだとかな。
046511NGNG
>>464
おおその通りだ。へたうった。例外はメンバポインタの場合だけだ
3.9.3.5 In this International Standard,
the notation {\it cv} (or {\it cv1}, {\it cv2}, etc.),
used in the description of Types,
represents an arbitrary set of cv-qualifiers,
0466デフォルトの名無しさんNGNG
なんとなく、ニュアンス的には、&aがアドレスなのは当たり前の前提事項だから、
適当にアドレスと書いたり書かなかったりしてしまってるように見える。
まあ断定は出来ないけど。
0467デフォルトの名無しさんNGNG
コピペできるpdfがほしい
0468デフォルトの名無しさんNGNG
>>467
% cp foo.pdf bar.pdf
できますが、何か? もしかしてパーミッションの問題か?
0469デフォルトの名無しさんNGNG
pdfコピペできるっしょ?
0470 NGNG
>>468
コピーしているようにしか見えないが、どこでペーストしてる?
0471デフォルトの名無しさんNGNG
>>470
foo.pdf で取り込み(コピー)、bar.pdf で貼り付け(ペースト)では?

# cp コマンドで名前変えて連続コピーってできたっけか?
# シェルスクリプト書く方が早そうだけど
0472デフォルトの名無しさんNGNG
int *i;
と
int* i;
の違いって何ですか?
0473デフォルトの名無しさんNGNG
*の位置
0474472NGNG
・・・・・。
0475 NGNG
>>472
違いはない。書き手のセンスの問題。
0476デフォルトの名無しさんNGNG
int * i;
0477デフォルトの名無しさんNGNG
int/*
Accept: */*
i
;
0478デフォルトの名無しさんNGNG
if (hoge) {

};

とかみたいにブロックの後に ; を付ける人が偶にいますが、
これってどうですか?
0479デフォルトの名無しさんNGNG
意図が見えない。
0480488NGNG
漏れのアクロバットリーダーでは
テキスト選択のボタンが使えなくなってる。なんでだろ。
0481デフォルトの名無しさんNGNG
ちゃんと ISO+IEC+14882-1998.pdf を購入した人なら、>>2 にある
html版の Final draft を使わせてもらってよいんじゃないかな。
つーか、html 化された正式版仕様書ってないの?
ちなみに >>5 にある ansi_iso_iec_14882_1998.pdf は海賊版ぽい。
ダウンロードした人の話では正式版とはファイルサイズが異なるらしい。
0482デフォルトの名無しさんNGNG
(ΦωΦ)フフフ・・・・for_eachサイコー
0483デフォルトの名無しさんNGNG
>>481 プ
ISO/IEC 14882は 2.8M 2.1M の2つのタイプが存在するのを知らないのか?
それから、なぜ正規購入者でなければwebのFDを利用できないんだ?
頭に虫沸いてない?
0484デフォルトの名無しさんNGNG
>>483
> ISO/IEC 14882は 2.8M 2.1M の2つのタイプが存在するのを知らないのか?
うん、知らない。2.8M のやつってどこが配布してるの? 2.1M のやつとは
何か違いがある?

> なぜ正規購入者でなければwebのFDを利用できないんだ
FD って一般に公開されてなかったと思ったから。実際のところ、FDの
ライセンスはどうなってるの?

上記2点、よければ教えてよ。
0485デフォルトの名無しさんNGNG
俺のは2.72Mだが何か?
0486デフォルトの名無しさんNGNG
structの使い方についての質問です。例えば、
struct A { int i; float f; };のようなstructを定義して、
これをmain()の中で、A *a=new a[10];(あるいは、A a[10];)
として、他の関数の中で使うには、その関数はどう定義
すればよいのでしょうか?void func(A* a[]){}ではダメでした。
ここでいうfunc()の中で、a[5]->iを使いたいのです。
よろしくお願いします。
0487デフォルトの名無しさんNGNG
>>478
struct{
...
};
でセミコロンをつけ忘れないように普段から慣れさせておくため。
0488デフォルトの名無しさんNGNG
>>486
void func(A a[]) ;
とか
void func(A *a) ;
0489486NGNG
自分で解決できました。この場合
void func(A a[10])でいいのですね。
0490489NGNG
>>488さん、ありがとうございます。
そちらのほうが良さそうですね。
a[10]としてしまうのとどう違うんでしょうか。
0491デフォルトの名無しさんNGNG
何故あなたはC++を使うのですか?
0492デフォルトの名無しさんNGNG
>>490
結果に違いはないです。 ないからわざわざ10と書くこたな(略
0493初心者NGNG
ないなら別に10と書いても(略
0494デフォルトの名無しさんNGNG
2文字余計にタイプするだけで指が疲れる。。
0495デフォルトの名無しさんNGNG
>>494
そんなこと言ったら、2chに書き込む方がよっぽど指が疲れるYO!
0496デフォルトの名無しさんNGNG
つか、10個の配列だよ、と断りを入れておけば、9個しか用意しないで呼び出したやつに文句(略
0497デフォルトの名無しさんNGNG
っていうか、C++なんだからvector使えYO!
0498デフォルトの名無しさんNGNG
>>493
C, C++ だと仮引数の配列はポインタに縮退するから、わざわざ a[10] と
書くのは

 誤解を助長してる

としか思えんなぁ。だいたい要素数 10 個の配列にしか適用できない関数って
時点で、何か間違ってるような気がする。

俺なら

1. 構造体にして、そのポインタを引き渡す
2. 要素数も同時に引数として渡す or vector 使う
3. 番兵を使う

どれかにするけどな。
0499デフォルトの名無しさんNGNG
C++初心者です.RECT構造体についての質問です.
RECT myrect;
---------------------------------------------------
myrect.top = 0;
myrect.left = 0;      問題はこの部分です
myrect.bottom = 100;
myrect.right = 100;
---------------------------------------------------
CreateHatchBrush(HS_CROSS,GetSysColor(COLOR_WINDOW));
FillRect(hwnd,&myrect,hbrush);
のようにして,ウィンドウの任意の領域を白紙に戻したいのですが,
RECT構造体(myrect)の(座標の)初期化がうまくいきません.
GetClientRect(hwnd,&myrect);
として座標を取得するしかないのでしょうか?
また,任意の領域を白紙に戻す方法でもっと良い方法があるんでしょうか?
よろしくお願いします.
0500かかしNGNG
あの相談したいことがあるのですか、
ここの掲示板に書くことではないと思うのですがどこに書けばいいか
分からないのでアドバイスをお願いします。

「DevelopperStudio」とは、何のことでしょうか?
探してもさっぱり  (+_+)
皆さん!!この件に関して知っていることがあれば
メールかRe>でお願いします。

@かかし
0501デフォルトの名無しさんNGNG
Developper Studioは探しても見つかりません。
Developer Studioを探して下さい。
0502499NGNG
解決しました.

RECT *root;

void Draw(void)
{
RECT *p = new RECT;
p->top = 0;
p->left = 0;
p->bottom =100;
p->right =100;
root = p;
}
とする事で代入できました.
ポインタを使ってしかメンバには代入できないのですね.
Cでは
RECT myrect;
のように構造体myrectを宣言すれば myrect.メンバ名
もしくは、myrectを指すポインタ->メンバ名
でアクセスできたのと思うのですが.
newもしくはmallocを使ってポインタの指す構造体を直接作らないと
いけないんですねえ.
間違いがあれば指摘お願いします.
0503デフォルトの名無しさんNGNG
&a で渡して、A(*)[10] 型で受け取るようにしたらどうだろう。
要素数を間違えて渡したらコンパイル時に型不一致で引っかかって
くれる。
0504デフォルトの名無しさんNGNG
>>499>>502
いってることがよくわからないんだけど…。
RECTみたいな単純な構造体メンバへのアクセスって別にCもC++もかわらないよ?
0505デフォルトの名無しさんNGNG
メンバ関数のポインタを使ってメンバ関数を呼び出そうとしているのですが、
class Base {
 void Function();
void Main();
 void (Base::*funcPtr)();
};
void Base::Main() {
 funcPtr = &Base::Function;
 (*funcPtr)(); // ここでエラー
}
としても
error C2171: '*' : 'void (__thiscall Base::* )(void)' のオペランドが無効です。
error C2064: 関数ポインタとして評価されない式を使って、関数を呼び出そうとしました。
とエラーが出てしまいます。
メンバ関数を呼び出す際は何か特別な構文などが必要なのでしょうか?
0506デフォルトの名無しさんNGNG
>505
(Base::funcPtr)();
とか
0507デフォルトの名無しさんNGNG
>>505
インスタンスを与えればよい。

class Base {
void Function();
void Main();
void (Base::*funcPtr)();
};
void Base::Main() {
Base b;
funcPtr = &Base::Function;
(b.*funcPtr)();
}
0508デフォルトの名無しさんNGNG
>>506
コンパイル通らないっすよ。
0509デフォルトの名無しさんNGNG
(this->Base::*funcPtr)()
0510506NGNG
>508
コンパイルは通った。リンクで引っかかるんだろ
つか、厨でした。逝ってきます
0511デフォルトの名無しさんNGNG
>>510
うーんコンパイラによるような。
BCC5.6だとコンパイルエラー。「メンバポインタの不正な使用」だとさ。
>>509
なるほど。その手があったか。
0512506NGNG
むう......うちのgccだと509がコンパイルエラーになる......何故?
0513デフォルトの名無しさんNGNG
>>505

class Base {
void Function();
void Main();
void (Base::*funcPtr)();
};
void Base::Main() {
funcPtr = &Base::Function;
(this->*funcPtr)();
}
051411NGNG
>>512
わざわざ指定するなら当然
(this->*Base::funcPtr)()
0515506NGNG
>513
>514
Oh!イケたよ!(コンパイルだけしか試してないが)
せんきゅう!
しかしなんでthis->が要るのかな?
0516デフォルトの名無しさんNGNG
「->*」「.*」が演算子なんだよな?

>>514 意味わかんない。
0517デフォルトの名無しさんNGNG
「->*」「.*」が演算子なんだよな?

ちゃう
0518513NGNG
Function宣言しかしてないやん…。。。
なんでリンク時にエラー吐くのかと思ったYO!

thisが必要なのは、関数ポインタは暗黙のthisが使われないとかなんとか。
0519506NGNG
>517
ん?あってるっしょ?「->*」「.*」で単独の演算子として優先順位と結合性が定義されてるみたいよ?
052011NGNG
>>516
>>506が>>509で困ってるようだったから

>「->*」「.*」が演算子なんだよな?

そう
0521506NGNG
>518==513
そうなのれすか。ややこしいなあ
0522デフォルトの名無しさんNGNG
メンバ関数へのポインタは通常の関数のポインタとは意味が違って、
単なるオフセットなのだそうだ。
だからインスタンスなりthisなりの実体を渡さないとコンパイルでき
ないのでは。
0523505NGNG
>>506-518
ありがとうございます。
funcPtr = &Base::Function;
でいかにして現在のオブジェクトのメンバであるかを表すのか
ということを考えていたのですが、ご指摘の通りthisポインタで
指定するということで解決することが出来ました。
本当にありがとうございました。
0524506NGNG
>522
???だったらメンバ変数と一緒じゃない???
あれ?なんか激しく勘違いしてるのかな?ごめ、もっとC++勉強してきます.....
0525デフォルトの名無しさんNGNG
>>522 ダウト
0526505NGNG
>>519
>>522
この関連記事だけで知らないことが2つも。
とても勉強になります。

そこまで詳しくC++の内側まで書いてある本は
どのような物があるのでしょうか?
0527デフォルトの名無しさんNGNG
>>526
>>5
052811NGNG
virtualな関数へのポインタはどういう実装が考えられる?
0529デフォルトの名無しさんNGNG
>>528 意味わかんない。
0530506NGNG
>528
フツーにインスタンスごとに関数ポインタ保持、じゃダメですかね?
ところでメンバ関数ってインスタンスごとに生成されたりしないよね?それともこの時点で間違ってる?
053111NGNG
うっひゃ〜〜〜〜〜
メンバ関数ポインタは12byteもあるのか。
上のほうでウソ書いちゃったな。ごめん

>>529
こういうのどう解決してるのかな〜と思って
#include <iostream>

struct A { virtual void f(void) { std::cout << "A" << std::endl ;}} ;
struct B : A { void f(void) { std::cout << "B" << std::endl ;}} ;

int main() {
A a, *p ;
B b ;
void (A::*f)(void) = &A::f ;

p = &a ;(p->*f)() ;
p = &b ;(p->*f)() ;
return 0 ;
}
0532 NGNG
>>531
> メンバ関数ポインタは12byteもあるのか。

実装によるだろ。VC++は4byteだし。

> こういうのどう解決してるのかな〜と思って

VC++の場合だと、void A::__call_f() {f();} のような関数を
勝手に作るみたいだ。
0533デフォルトの名無しさんNGNG
>>531
仮想関数の場合、BCCでコンパイルしてTurbo Debuggerで中身を
覗いてみたら、インスタンスの生成時にメンバ関数へのアドレスを
保持しているみたい。
0534デフォルトの名無しさんNGNG
struct cls {
 int f();
 int f() const;
};
cls c;
main() {
 c.f(); /***/
}

/***/のところでconstのほうを呼ぶ方法ありますか?
053511NGNG
>>532
>実装によるだろ
ハハハ、そんな当然のこと書かんでもいいって

>void A::__call_f() {f();}
なるほどね〜。それは簡単だ

>>533
仮想関数テーブルのこと?
0536デフォルトの名無しさんNGNG
>>534
struct cls {
void f() { cout << "f()" << endl; }
void f() const { cout << "f() const" << endl; }
};

cls c;
const cls cc;

int main() {
c.f();
cc.f();
}
0537デフォルトの名無しさんNGNG
>>535
ははあ、これが仮想関数テーブルなのでしょうか。Aのインスタンスには
一つ、Bのインスタンスには二つのアドレスを代入しています。
0538 NGNG
>>534
static_cast<const cls&>(c).f();
0539534NGNG
>>536
ねた?非constオブジェクトから呼ぶには?
0540デフォルトの名無しさんNGNG
>>538>>539
struct cls {
void f() { cout << "f()" << endl; }
void f() const { cout << "f() const" << endl; }
};

cls c;
const cls cc;

int main() {
c.f();
const_cast<const cls &>(c).f();
}

でもよいようだ。
0541デフォルトの名無しさんNGNG
const_castじゃないの?
0542534NGNG
>>538
やはりキャストかconstとして他の関数に渡すしかない?
0543デフォルトの名無しさんNGNG
>>537
なんかよくわからんな。bccは

>>534
じゃあ、私もねたを一つ
(c.*(int(cls::*)()const)&cls::f)();
0544デフォルトの名無しさんNGNG
初めてconst_castの使い方がわかったよ。

int main() {
c.f();
const_cast<const cls &>(c).f();
cc.f();
const_cast<cls &>(cc).f();
}
0545デフォルトの名無しさんNGNG
>>543
多分、BをAにダウンキャストした時にAのメンバ関数が正しく呼ばれる
ようにアドレスを二つ代入しておく必要があるのでしょう。

それと、そのキャストすごいですね。
0546デフォルトの名無しさんNGNG
>>534
int f(); のほうを別の名前にしてください。

同じ名前なのに自然に使い分けれないって状態が問題だと思うんだけど、どうよ。
0547534NGNG
>>546
実際は
iterator begin();と
const_iterator begin() const;
なのよ・・・。
0548デフォルトの名無しさんNGNG
>>546
これは関数の多重定義になっているみたいですね。呼び出す
インスタンスがconst型かそうでないかで呼び出す関数が変わる
ようです。
■ このスレッドは過去ログ倉庫に格納されています