C++相談室 part58

このエントリーをはてなブックマークに追加
1v(^・^)v
C++に関する質問やら話題やらはこちらへどうぞ。
ただし質問の前にはFAQに一通り目を通してください。
IDE (VC++など)などの使い方の質問はその開発環境のスレに
お願いします。

テンプレその他 >>2-15 付近参照

前スレ(実質 part57)
C++相談室 part56
http://pc11.2ch.net/test/read.cgi/tech/1185377587/
2v(^・^)v:2007/09/26(水) 03:41:45
■基本■
[C++ FAQ]
 http://www.parashift.com/c++-faq-lite/
 http://www.bohyoh.com/CandCPP/FAQ/ (日本語)
  Cとその仕様を比較しながらの解説なので分かりやすい。
  ***** 質問の前に必ずこの二つに目を通してください *****
[C/C++ リファレンス]
 http://www.cppreference.com/ (英語)
 http://www.cppll.jp/cppreference/ (↑の日本語訳だけど最新は反映しない)
[禿 Stroustrup]
 http://public.research.att.com/~bs/
[C++ International Standard]
 http://www.iso.org/iso/iso_catalogue/catalogue_tc/catalogue_detail.htm?csnumber=38110
[JTC1/SC22/WG21 - C++]
 http://www.open-std.org/jtc1/sc22/wg21/
  ここから規格の最新(2003より新しい)ドラフトがダウンロードできる。
[JIS X3014]
 http://www.jisc.go.jp/app/pager?&RKKNP_vJISJISNO=X3014
  ISO規格の日本語訳。JIS X 3014:2003はISO/IEC 14882:2003 (E)に対応。
3v(^・^)v:2007/09/26(水) 03:42:22
4v(^・^)v:2007/09/26(水) 03:42:53
5v(^・^)v:2007/09/26(水) 03:44:42
6v(^・^)v:2007/09/26(水) 03:45:13
1 ttp://piza.2ch.net/tech/kako/980/980175292.html
2 ttp://pc.2ch.net/tech/kako/996/996640937.html
3 ttp://pc.2ch.net/tech/kako/1003/10038/1003832761.html
4 ttp://pc.2ch.net/tech/kako/1009/10090/1009071535.html
5 ttp://pc.2ch.net/tech/kako/1014/10142/1014217496.html
6 ttp://pc.2ch.net/tech/kako/1018/10184/1018454705.html
7 ttp://pc.2ch.net/tech/kako/1021/10217/1021787032.html
8 ttp://pc3.2ch.net/tech/kako/1025/10250/1025010364.html
9 ttp://pc3.2ch.net/tech/kako/1027/10273/1027347982.html
10 ttp://pc3.2ch.net/tech/kako/1029/10293/1029315669.html
11 ttp://pc3.2ch.net/tech/kako/1032/10323/1032345774.html
12 ttp://pc3.2ch.net/tech/kako/1035/10350/1035005882.html
13 ttp://pc3.2ch.net/tech/kako/1038/10380/1038031395.html
14 ttp://pc5.2ch.net/tech/kako/1041/10413/1041328679.html
15 ttp://pc5.2ch.net/tech/kako/1043/10436/1043605481.html
16 ttp://pc5.2ch.net/tech/kako/1045/10457/1045746245.html
17 ttp://pc5.2ch.net/tech/kako/1047/10475/1047560042.html
18 ttp://pc5.2ch.net/tech/kako/1050/10501/1050177746.html
19 ttp://pc5.2ch.net/tech/kako/1052/10526/1052625846.html
20 ttp://pc5.2ch.net/tech/kako/1055/10551/1055162298.html
21 ttp://pc5.2ch.net/tech/kako/1057/10575/1057580107.html
22 ttp://pc5.2ch.net/tech/kako/1060/10603/1060361082.html
23 ttp://pc5.2ch.net/tech/kako/1062/10626/1062690663.html
24 ttp://pc5.2ch.net/tech/kako/1066/10665/1066546387.html
25 ttp://pc5.2ch.net/tech/kako/1067/10679/1067949669.html
26 ttp://pc5.2ch.net/test/read.cgi/tech/1070164402/ (迷子)
27 ttp://pc5.2ch.net/test/read.cgi/tech/1074454641/ (迷子)
28 ttp://pc5.2ch.net/test/read.cgi/tech/1077985164/
29 ttp://pc5.2ch.net/test/read.cgi/tech/1082047479/
30 ttp://pc5.2ch.net/test/read.cgi/tech/1084030770/
7デフォルトの名無しさん:2007/09/26(水) 03:57:30
  _____ 
  (すた☆らき)
   ̄ ̄\| ̄ 
http://www.freewebs.com/premiumtv/?X3/?STV=%E3%82%89%E3%81%8D+%E3%81%99%E3%81%9F
8v(^・^)v:2007/09/26(水) 04:08:11
9v(^・^)v:2007/09/26(水) 04:08:43
■関連スレ■
多すぎ。とりあえずスレタイ C++ で検索して。
以下、スレタイで見付からなさそうな関連スレ。

Boostを語れゴラァ part4
http://pc11.2ch.net/test/read.cgi/tech/1175663346/l50
GCCについて part7
http://pc11.2ch.net/test/read.cgi/tech/1145357824/l50
Cygwin + MinGW + GCC 相談室 Part 3
http://pc11.2ch.net/test/read.cgi/tech/1177944767/l50
10v(^・^)v:2007/09/26(水) 04:10:15
テンプレ終了。 ISO のリンクが "301 Moved permanently" だったんで更新しといた。
11デフォルトの名無しさん:2007/09/26(水) 04:38:06
ぉぉ。すごい。乙です。
12デフォルトの名無しさん:2007/09/26(水) 04:38:46
注:私の有意義な発言に対し、自分の理解不足を棚に上げ煽り、1行レス
で返す方が多いようですが、そのような方はスレの皆様を混乱させるだけでなく
スレの雰囲気を崩しかねないのでお黙り下さい。
また質問者は回答者に知識を披露する場を与える貴重な存在なので、
質問者を見下した回答、あまりにも儀礼を欠いた回答も厳重に禁止いたします。
忙しい中、少ない時間の合間を縫って質問しに来てるわけですので、
その辺ご承知下さい。なお、当方が質問に対して有意義な答えであると
判断した方には評価いたしますので各自よく調べ、よく考え正確な回答をするように。
13デフォルトの名無しさん:2007/09/26(水) 07:30:25
STLつかうと一気に実行ファイルサイズが10倍に?!

環境によるだろ。
俺はBorland-C++5.6.2に -D_RTLDLL オプションを指定して、極力
ランタイムを使用するようにして使っているが、例えばstd::vectorを
使っても使わない時と比べ10Kほどしか増えない

すげえ。ダイナミックリンクしといてファイルサイズが増えないとかいってるよ。この人。
14デフォルトの名無しさん:2007/09/26(水) 07:31:09
C1010: プリコンパイル済みヘッダーの検索中に予期しない EOF を検出しました。
とかいうエラーが出るんだけどこれってどうすればいいの?

#include <stdafx.h>
後死ね。

言葉が悪いな。それで教えているつもりか。
まぁヒントぐらいにはなったな。
うむごくろう。
15デフォルトの名無しさん:2007/09/26(水) 10:56:04
やっぱり貼られるんだなこれ
16デフォルトの名無しさん:2007/09/26(水) 11:17:02
地鎮祭が済んだな乙
17デフォルトの名無しさん:2007/09/26(水) 11:35:06
そこまでがテンプレだからな。
18デフォルトの名無しさん:2007/09/26(水) 12:00:46
stlとかboost使いまくったら通常は1M程度で住むものが
10M超えたりするんでしょうか?
19デフォルトの名無しさん:2007/09/26(水) 12:07:37
「通常」の定義がわからん
20デフォルトの名無しさん:2007/09/26(水) 12:15:08
それでは、よくある「クラスと継承が使えるbetter Cとして書いたC++のコード」を「通常」だと想定して答えて下さい
今作ってるものがboostをヴァリヴァリに使っているので
それと比較すればどれぐらいバイナリサイズは肥大するのかがちょっと気になります
21デフォルトの名無しさん:2007/09/26(水) 12:25:32
バイナリサイズよりコンパイル時間の肥大が気になる。
22デフォルトの名無しさん:2007/09/26(水) 12:28:21
通常、増える場合と減る場合、そして変わらない場合があります。
23デフォルトの名無しさん:2007/09/26(水) 12:33:21
全スレ

>827 名前:デフォルトの名無しさん 投稿日:2007/09/22(土) 23:20:47
>emacsでc++開発をするときの環境に関するサイトってないでしょうか?

flymake
http://d.hatena.ne.jp/pyopyopyo/20070715/p1
24デフォルトの名無しさん:2007/09/26(水) 19:15:43
>>22
何そのトートロジー
25デフォルトの名無しさん:2007/09/26(水) 20:27:10
 int data[10] ={10,20,30,40,50,60,70,80,-999} このようなint配列があります       配列の内容を実行結果のように表示するプログラムを作りなさい         -999になれば処理を終了します 
 ポインタを固定して表示させる処理とポインタを変化させて表示させる処理の2つ作成しなさい 
 この内容がわからないので教えて下さいお願い致します
26デフォルトの名無しさん:2007/09/26(水) 20:31:33
なんだマルチか
27デフォルトの名無しさん:2007/09/26(水) 21:52:11
スレ建て乙
28デフォルトの名無しさん:2007/09/27(木) 00:22:22
>>1 おつかれ >>10 GJ!
有用なサイトを手っ取り早く見つける方法...
それはテンプレを見ることだ。
29デフォルトの名無しさん:2007/09/27(木) 00:22:33
int *p = data;
int i = 0;

while(*p++ != 999) std::cout << *p << std::endl;
while(*(p + i) != 999) std::cout << *(p + i) << std::endl;
30デフォルトの名無しさん:2007/09/27(木) 01:55:53
999ではなく-999
2つ目のループ前にpを初期化しないといけない
31デフォルトの名無しさん:2007/09/27(木) 09:48:49
C++で書かれた、正規表現処理クラスみたいなものってありませんか?
32デフォルトの名無しさん:2007/09/27(木) 10:00:16
boost/random.hpp
33デフォルトの名無しさん:2007/09/27(木) 10:00:50
ミスった。
boost/regex.hpp
34デフォルトの名無しさん:2007/09/27(木) 10:25:06
!?
35デフォルトの名無しさん:2007/09/27(木) 10:57:19
double a[3000][3000];
て定義すると蹴られるんだけど、なんでかわかる人いますか?
36デフォルトの名無しさん:2007/09/27(木) 11:09:59
環境は?
37デフォルトの名無しさん:2007/09/27(木) 11:14:19
VC6のSDKでウィンドウを持ったクラスの継承がしたいです。
Hoge1クラス:メインウィンドウになるクラス
Hoge2クラス:継承元となるウィンドウを持ったクラス
Hoge3クラス:Hoge2クラスを継承したクラスでHoge1ウィンドウのボタンを押したときに表示されるウィンドウを持ったクラス

Hoge2クラスはWinProcをstaticでクラス内に入れています。クラスの登録やウィンドウを生成する関数はprivateとして存在します。
Hoge3クラスも同じような構成です。
で、Hoge3クラスで不用なメッセージ処理はHoge2のウィンドウクラスに回してやりたいのですが、
その方法がいまいちわかりません。手順・・がいまいちです。
Hoge3クラスの登録をする前に、Hoge2クラスのウィンドウを登録する必要があると思い、
WNDCLASSEXを使ってウィンドウの登録をする?と思いきや、横取りするHoge2にあるプロシージャとかも指定しないといけないわけですよね?
でもこの段階だと、Hoge2クラスの存在すら誰も知らないわけで・・・この辺りがよくわかりません。
ボタンのスーパークラス化と同じようなイメージでいるのですが、ボタンの場合は
ウィンドウズが予めその存在を認識しているからGetClassInfoExを使って情報を取得する
ことができますが、自作ウィンドウクラスの場合はそれができなくて・・・
38デフォルトの名無しさん:2007/09/27(木) 11:16:33
>>35
俺のエスパー能力が、環境がx86なPCであると言っている。
さらに、かなりの確率でWindowsであると言っている。
さらに、俺のエスパー能力はこう言っている。

コンパイラ「スタック足りねーよボケッ!」

ttp://www.google.com/search?&q=8+*+3000+*+3000+byte
39デフォルトの名無しさん:2007/09/27(木) 12:15:58
>>35
配列が大きすぎてスタック領域が足りてない。と思われる。
巨大な配列を宣言するときは new するか static にするべき
40デフォルトの名無しさん:2007/09/27(木) 12:28:43
俺の環境ではgcc 3.4やvc2005でも文句言われないんだけど…
そのかわり実行時にスタックオーバーフロー
そういうオプションでもあるの?
41デフォルトの名無しさん:2007/09/27(木) 12:34:20
>>35
誰に蹴られるって?
42デフォルトの名無しさん:2007/09/27(木) 12:38:23
>>41
金色のファルコ
43デフォルトの名無しさん:2007/09/27(木) 21:58:29
>>39
必要ないのに無駄にnewなんか使うなよ。
どうしてもSTLは使いこなせないってことなら話は別だが。
44デフォルトの名無しさん:2007/09/27(木) 21:59:28
>>37
1. 静的メンバ関数となっているHoge2のウィンドウプロシージャから
仮想関数にしたウィンドウプロシージャを呼ぶようにして、
Hoge3でそれをオーバーライドする。
Hoge3では新たなウィンドウクラスを登録しない。

2. Hoge2のWinProcをprotectedにして、Hoge3のウィンドウプロシージャでは、
DefWindowProcの代わりにHoge2::WinProcを呼ぶようにする。
Hoge3では新たなウィンドウクラスを登録する必要がある。

俺は1をよくやる。2こそはスーパークラス化だな。
ウィンドウプロシージャの仮想関数化はここが参考になる。
http://techtips.belution.com/ja/vc/0009/
http://www.google.com/search?q=cache:http://techtips.belution.com/ja/vc/0009/

45デフォルトの名無しさん:2007/09/28(金) 00:17:35
>>43
スタックじゃサイズ足らないって理由だけでnewすんのもSTL使うのも大差ないだろ
4637:2007/09/28(金) 01:30:59
>>44
そこは何度も見てるのですが・・・。そこに書いてあるクラスは、
それを継承させると簡単にサブクラス化できたり元に戻せたりする
クラスってことですよね?
47デフォルトの名無しさん:2007/09/28(金) 02:05:57
>>37
>で、Hoge3クラスで不用なメッセージ処理はHoge2のウィンドウクラスに回してやりたいのですが、
>その方法がいまいちわかりません。手順・・がいまいちです。

Hoge3 クラスは Hoge2 クラスを継承してるんだから、ただ単に継承元クラスのメンバ関数を呼ぶだけでいいのでは
ムダに難しいこと考えてない?

Windows に登録するウィンドウクラスと C++ のクラスが一致してる必要はないよ
C++ のクラスを継承してるからってウィンドウクラスをスーパークラス化したりサブクラス化したりする必要はない
48デフォルトの名無しさん:2007/09/28(金) 07:38:08
インナークラスっておまいら普通に使ってる?
49デフォルトの名無しさん:2007/09/28(金) 08:10:15
pimplの形でなら使ってるよ
50デフォルトの名無しさん:2007/09/28(金) 09:32:02
>>45
大差なくはない。vector使え。
例外安全な上に組込配列よりずっと便利だ。
51デフォルトの名無しさん:2007/09/28(金) 10:11:22
2
4
16
256
65536
4294967296 * sizeof(double) = 8589934592b = 8192MB
52デフォルトの名無しさん:2007/09/28(金) 10:15:48
そこまでいったら流石にメモリマップドファイル使う
5337:2007/09/28(金) 10:45:46
>>47
「ウィンドウ作成データとして、CWinBase クラスの派生クラス CxxxWnd オブジェクトを指定することを忘れないで下さい。」
が、何を指しているのかわからないです。どこにCxxxWnd オブジェクトを指定するのでしょう?
5437:2007/09/28(金) 10:50:39
WNDCLASSEXを登録するとき、サンプルではBaseWnd::WindowMapProcを指定
しろとあるけど、指定するものを自分自身のWinProcを指定してやり
Attachを呼べばいいのかな?
55デフォルトの名無しさん:2007/09/28(金) 11:00:24
>>53
それは、CreateWindowExの最後の引数。
CxxxWnd wnd;
CreateWindowEx(..., &wnd);
こういう感じ。CreateWindow(Ex)の引数は
WM_CREATEまたはWM_NCCRAETEでCRATESTRUCTとして全て参照できる。

いつもこうしなければならないだから、
CreateWindowExもクラスのメンバにしてこの処理はしばしば隠蔽される。

そろそろスレ違いが近付いているぞ。
5637:2007/09/28(金) 11:29:40
>>55
今そこ調べてました・・・
ttp://nomina.petit-archives.mydns.jp/tests/old/gecko012/nmnConsoleControl.cpp
ttp://www7a.biglobe.ne.jp/~lshen/EternalWindows/WinBase/Window/Window08.html


>>そろそろスレ違いが近付いているぞ。
もうすこし付き合ってください・・
その最後の引数に&wndを渡して自身のメンバ変数や関数にアクセス
する場合、が微妙です。
WM_CREATEで
LPCREATESTRUCT lpcs = (LPCREATESTRUCT)lParam
というところはOKです。ここから自分のメンバにアクセスする方法が
いまいちです。
57デフォルトの名無しさん:2007/09/28(金) 11:33:18
死ね
5837:2007/09/28(金) 11:33:38
static Hoge3* pWnd = NULL;
pWnd = (Hoge3*)(((CREATESTRUCT*)lp)->lpCreateParams);
こんな感じか?な?

59デフォルトの名無しさん:2007/09/28(金) 11:36:24
CxxxWnd *wnd = (CxxxWnd*)lpcs->lpCreateParams;
6037:2007/09/28(金) 11:37:44
>>55
できますた。ありがとうございます!
あとは54なんですが・・・これがまた・・・orz
61デフォルトの名無しさん:2007/09/28(金) 11:38:16
死ね
62デフォルトの名無しさん:2007/09/28(金) 11:42:22
63デフォルトの名無しさん:2007/09/28(金) 12:11:35
>>58
そこでstaticはやめとけ。

>>60
Hoge2::WinProcに相当するのが、44の指したページで言うCWndBase::WindowMapProc。
6437:2007/09/28(金) 12:38:27
class Hoge:public CWndBase
  public:
   BOOL InitInstance( HINSTANCE hInstance );
  private:
   //オーバーライドしたWndProc
 static LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam);
};

使うとき、

Hoge hoge;
hoge.InitInstance(hInstance);

InitInstanceの中ではウィンドウの登録、作成をする
  WNDCLASSEX wcex;
  :
  wcex.lpfnWndProc = (WNDPROC)BaseWnd::WindowMapProc;//WndProc;
  :
  RegisterClassEx(&wcex);

で、CreateWindowする。最後の引数はthisを渡す。

こうすると、メッセージは、まずWindowMapProcで処理されて、
BaseWndのWndProcへ飛んできます。が、オーバーライドした自分のWndProcには飛んでこない
です。CreateWindow後のAttachとか呼んでみたのですが、変わらずです。
なんか、おしい気がするのですが、ぜんぜんですかね?
65デフォルトの名無しさん:2007/09/28(金) 12:43:20
なぜ static が付いてる?
それでオーバーライドになってると思ってるのか?
66デフォルトの名無しさん:2007/09/28(金) 12:48:32
>>64
44のページを良く見ろ。
WindowMapProcはstaticで、WndProcはvirtualだ。
静的メンバ関数で多態的なオーバーライドは不可能だ。
67デフォルトの名無しさん:2007/09/28(金) 12:49:18
お前らの優しさに嫉妬
6837:2007/09/28(金) 13:29:59
あ、static付いてる。コールバックはstatic付けることで解決、なんての
ばかり気にしてたので、普通につけちゃいました。
で、取ったらコンパイラ エラー C2555が出て、「そんなの聞いてませんが何か?」
とか思いつつ、調べること数分、どうにかメッセージを受信するとこまで
できたようです。
今は、慣れてないのにいろんなことやってしまった(気でいる)ので、
これから1つ1つ整理して、ちゃんとしたものを作っていきます。
みなさまありがとうございました。
69デフォルトの名無しさん:2007/09/28(金) 14:22:21
やれやれ ┐(´ー`)┌
70デフォルトの名無しさん:2007/09/28(金) 14:33:43
でさ、なんでこの話題がC++スレで?
71デフォルトの名無しさん:2007/09/28(金) 15:26:42
相手する低脳がいるから
72デフォルトの名無しさん:2007/09/29(土) 08:31:08
class A{
 int a[10];
public:

}
73デフォルトの名無しさん:2007/09/29(土) 08:34:44
途中で書いてしまいました失礼しました

class A{
 int a[10];
public:
 int *get_a(){return a;}
}

int main(){
 int *p;
 p = get_a();
 for(int i = 0; i < 10; i++){
  p[i] = ...
  ... = p[i];
 }
 return 0;
}

このようなコードってカプセル化を壊してますか?
74デフォルトの名無しさん:2007/09/29(土) 08:40:45
>>73 うん。少し。
7573:2007/09/29(土) 08:45:15
やはり配列のポインタを返すというのはまずいのでしょうか?
76デフォルトの名無しさん:2007/09/29(土) 08:48:46
>>75 うん。少し。
77デフォルトの名無しさん:2007/09/29(土) 10:23:23
>>78 うん。少し。
78デフォルトの名無しさん:2007/09/29(土) 12:03:52
やはり>>77さんは早漏なのでしょうか?
79デフォルトの名無しさん:2007/09/29(土) 12:37:28
早漏は経験をつめば治ります。めげずに頑張りましょう。
80デフォルトの名無しさん:2007/09/29(土) 17:31:27
こんな感じにしちゃえば?
int get_a( int i ){return a[i];}
81デフォルトの名無しさん:2007/09/29(土) 21:08:11
代入は?
82デフォルトの名無しさん:2007/09/29(土) 21:12:06
>>81
int& get_a(int i) { return a[i]; }
int get_a(int i) const { return a[i]; }

83デフォルトの名無しさん:2007/09/29(土) 21:22:13
effective C++読めよー。
84デフォルトの名無しさん:2007/09/29(土) 21:44:16
っていうか言語以前の問題だろ。
っっていうか全部ネタだろ。
85デフォルトの名無しさん:2007/09/29(土) 23:56:29
なんで誰も内部ハンドルを返すのは云々って言ってあげないのか
86デフォルトの名無しさん:2007/09/29(土) 23:58:29
>>85
流れ嫁よ
87デフォルトの名無しさん:2007/09/30(日) 08:55:39
hoge.hの中で
class hoge {
public:
virtual double CalcF1(Double_t r) const throw(std::exception);
}

hoge.cxxの中で
double hoge::CalcdF1dr(Double_t r) const throw(std::exception)
{
}

としてるんだけど、g++でcompileしようとすると
src/hoge.cxx: In member function 'virtual double hoge::CalcdF1dr(Double_t) const':
src/hoge.cxx:87: error: expected primary-expression before ';' token
と怒られます。どこが書き方間違ってるんでしょうか。
88デフォルトの名無しさん:2007/09/30(日) 08:56:33
あ、ごめん。
class hoge {
public:
virtual double CalcdF1dr(Double_t r) const throw(std::exception);
}
でした。
89デフォルトの名無しさん:2007/09/30(日) 08:57:57
あ、ごめん。勘違い。
スルーして下さい。
90デフォルトの名無しさん:2007/09/30(日) 18:33:43
VC2003で作られた 静的なlibは、
VC2005でリンクすることは不可能なんですか?
91デフォルトの名無しさん:2007/09/30(日) 20:19:13
クラスの内側で定義したクラステンプレートを特殊化する、

class X {
  template<typename T> class Y {};
  template<> class Y<int> {};
};

のようなコードは、VC++(2003/2005)ではコンパイルできますが、g++3/4では
error: explicit specialization in non-namespace scope ‘class X’ というエラー
になってしまいます。

Y<int>をXの中ではなく、名前空間スコープで
template<> class X::Y<int> {};
と書けばg++でもVC++でも問題なく特殊化できることは知っているのですが、
なんとかg++で、特殊化されたクラスの定義をXの中に書く方法はないでしょうか?

Y<T>とY<int>の定義が離れた場所にあると、コードが読みにくいと思うのです。

boost(特にmpl)の使用は歓迎です。
よろしくおねがいします。
92デフォルトの名無しさん:2007/09/30(日) 20:27:59
>>89
クラス末尾にセミコロンがありませんでした。ごめんなさい。

とちゃんと書こうYO!
93デフォルトの名無しさん:2007/09/30(日) 20:42:48
>>91
定義位置を近づけたいなら、両方クラス外に書けばいいんじゃね?
9491:2007/09/30(日) 20:45:33
>>93
ああ、たしかにそうですね。他に案がなければそうしたいとおもいます。

ただ、Y<T>とY<int>を両方クラス内に書けると、宣言と定義の位置も離れない(定義だけになる)ので、
より読みやすいと思っています。

というわけで、引き続きお願いします。
95デフォルトの名無しさん:2007/09/30(日) 20:54:22
>>91
規格ではネストされたクラス内での明示的特殊化は禁止されているけど
部分特殊化はOKなので、

class X {
  template <typename T, class U = void> class Y {};
  template <typename T>
  class Y< T
      , typename boost::enable_if<
         typename boost::is_same< T, int>
       > > {};
};

のようにenable_ifとis_sameを使って書くといいっぽい(初心者スレから一部拝借w)
VCでコンパイル可能なのはmsの独自拡張でgccの方が正しいとのこと
9691:2007/09/30(日) 20:57:38
なお、メンバ関数テンプレートで同様のエラーをくらう件については
(下記の2行めがエラーになる)、

class X {
  template<typename T> void foo(T x) {}
  template<> void foo<int>(int x) {} // error
};

下記方法でごまかしています。

#include <boost/type.hpp>
class X {
  void foo_(int x, boost::type<int>) { /* specialized */ }
  template<typename T> void foo_(T x, ...) {}
public:
  template<typename T> void foo(T x) { foo_(x, boost::type<T>()) ;}
};
9791:2007/09/30(日) 20:59:12
>>95
部分特殊化はOKだったんですか。気づきませんでした。
早速試してみます。どうもありがとう〜!!
98デフォルトの名無しさん:2007/09/30(日) 21:00:46
>>91
私はC++初心者ですが、>>93さんと同意見です。
>>95さんの言うようにgccの方が正しい(つまり規格どおりということですよね)ならば、
なおさらそう思います。

それに、Xクラスの定義を見たいときには、むしろYは外にあった方が見やすいのではないでしょうか?
99デフォルトの名無しさん:2007/09/30(日) 21:06:58
ちなみに関数テンプレでもこの手は使えるようだ
この手法も名前があったと思うけど思い出せない
使うなら適当にローカルなメタ関数を専用の名前空間に自作して階層を浅くする工夫が必要だね
使ってればわかるけど、凄く見にくくなるから
100デフォルトの名無しさん:2007/09/30(日) 21:10:12
あ、::type付けわすれた…
101デフォルトの名無しさん:2007/09/30(日) 21:43:54
読み易くするのが目的で読みにくくなる手法を選ぶか。
>>99 名前があるならソレをコメントに書いておけば良いかも。
102デフォルトの名無しさん:2007/09/30(日) 22:00:44
>>98 >>101
読みやすいかどうかは読み手にもよるし、あまり>>91>>94はよい聞きかたではなかったですね。
C++のコードを自動生成するツール(自作)の都合でX内に定義を書けると嬉しい、というのが実際の事情です。
10391:2007/09/30(日) 22:32:03
102は91です。

>>99
concept-controlled polymorphism ですか?
104デフォルトの名無しさん:2007/09/30(日) 23:06:47
>>100
> あ、::type付けわすれた…
検索エンジン経由で来るひとのために、一応訂正版貼っときますね。

#include <cstdio>
#include <boost/utility/enable_if.hpp>
#include <boost/type_traits/is_same.hpp>

struct X {
  template<typename T, typename U = void> struct Y {
    Y() { std::printf("genecic\n"); }
  };
  template<typename T> struct Y <T, typename boost::enable_if<boost::is_same<T, int> >::type> {
    Y() { std::printf("specialized for int\n"); }
  };
};
class Z {};

int main() {
  X::Y<Z> a;
  X::Y<int> b;
  X::Y<float> c;
}

実行結果は、
genecic
specialized for int
genecic
です。
10591=104:2007/09/30(日) 23:31:30
boostが使えない場合は、VC++2003/2005/g++対応だけ考えるならこんな感じでしょうか。
#include <cstdio>
namespace b00st {
  template <bool B, class T = void>
  struct enable_if_c {
    typedef T type;
  };
  template <class T>
  struct enable_if_c<false, T> { /* NO TYPEDEF! */ };
  template <class Cond, class T = void>
  struct enable_if : public enable_if_c<Cond::value, T> {};
  template<bool b> struct bool_ {
    static const bool value = b;
  };
  template<typename T, typename U>
  struct is_same : bool_<false> {};
  template<typename T>
  struct is_same<T, T> : bool_<true> {};
}
using namespace b00st;
struct X {
  template<typename T, typename U = void> struct Y {
    Y() { std::printf("genecic\n"); }
  };
  template<typename T> struct Y<T, typename enable_if<is_same<T, int> >::type> {
    Y() { std::printf("specialized for int\n"); }
  };
};
そろそろウザいとおもうので、これで打ち止めにします。ありがとうございました。
106デフォルトの名無しさん:2007/09/30(日) 23:40:10
このtemplate感、実に小気味良い 久しぶりにC++スレを実感した
107デフォルトの名無しさん:2007/10/01(月) 00:01:02
キモ
108デフォルトの名無しさん:2007/10/01(月) 00:04:13
小気味良いのは確かだけど、言葉遣いが丁寧すぎてちょっと痒い、というのが俺の感想。
うん、俺の感想なんかどーだっていいってのは承知。
109デフォルトの名無しさん:2007/10/01(月) 02:02:08
>>99
enable_ifの関数テンプレへの適用で質問。ある条件で2つの関数を呼びわけたいときは、こんな感じにすればいいみたいだけど、
  template<typename T>
  static void foo(T t, typename boost::disable_if<boost::is_same<T,int> >::type* = 0) {
  }
  template<typename T>
  static void foo(T t, typename boost::enable_if<boost::is_same<T,int> >::type* = 0) {
      // intへの特殊化版
  }
3つ以上を呼びわけるにはどうすれば? たとえば、
  template<int V>
  static void boo(typename boost::enable_if_c<V == 0>::type* = 0) { }
  template<int V>
  static void boo(typename boost::enable_if_c<V == 1>::type* = 0) { }
  template<int V>
  static void boo(typename boost::disable_if_c<V == 0 || V == 1>::type* = 0) {
     // default
  }
とかだと、default caseな関数の引数が大変なことになってしまうような。
boostスレのほうがいいのかな。。
110デフォルトの名無しさん:2007/10/01(月) 02:51:44
複雑な場合はmplの出番になるんじゃないかな

mpl::if_< ...,
mpl::if_< ...,

> >::type::call();
111109:2007/10/01(月) 03:23:49
>>110
すみません、それはどこに書くコードなんでしょうか?
call() とは一体。。

112109:2007/10/01(月) 03:28:24
>>110が理解できず、独自に考察を進め中。
  template<int V>
  static void boo(typename boost::enable_if_c<V == 0>::type* = 0) {}
は、
  template<int V>
  static void boo(typename boost::enable_if<
                    boost::is_same<
                      boost::mpl::int_<V>,
                      boost::mpl::int_<0>
                    >
                  >::type* = 0) {}
であり、さらに
  template<int V>
  static void boo(typename boost::enable_if<
                    typename boost::mpl::lambda<
                      boost::is_same<
                        boost::mpl::_1,
                        boost::mpl::int_<0>
                      >
                    >::type::apply<boost::mpl::int_<V> >::type
                  >::type* = 0) {}
だから、この数値0-Nでlambdaしたのをmpl::listで抱えて、特殊化版はlistのat<i>したのでenable_ifして、default版はこれらをandでfoldしたのにdisable_ifすればいいと思うんだぜ?

・・・絶対方向が間違ってる。
113デフォルトの名無しさん:2007/10/01(月) 03:37:53
いや、単に、mpl::if_で関数を実装したクラスを選んで呼び出す
boost/smart_cast.hppが参考になるかも
114デフォルトの名無しさん:2007/10/01(月) 03:44:43
>>113
私は、単に boo(0); boo(1); boo(2); とだけ書くと、呼び先の関数がコンパイル時に決まるようにしたいと
思っているんですが、>>110は、このbooを *呼ぶ側* をif_で工夫しろということ?

まぁ、boo()でif_を使って、適切なboo_()を呼ぶようにしてもいいのかもしれませんが、
委譲してしまうとタグディスパッチと大差ないようにも思うし。。

なんか勘違いしてたらすんません。smart_castは早速見てみます。
115デフォルトの名無しさん:2007/10/01(月) 04:37:09
どうしてもenable_ifを使いたいなら
複雑な条件を書かずに済ますことは不可能だと思う
116109:2007/10/01(月) 05:41:56
>>115
enable_ifが使いたいわけでは無くて、

1.メンバ関数テンプレートの特殊化(相当のこと - オーバーロードでもいい)を行いたい
2.特殊化の定義は、クラス内に書きたい (>>91と同じく, 見た目の問題で)
3.メンバ関数を呼ぶ側はあまり難しいことを考えたくない
4.タグディスパッチのような別関数への処理の委譲は、できれば避けたい (これも見た目の問題で)

という条件で、Pという場合と!Pという場合の処理の振り分けだったら、
enable_ifを使ったオーバーロードでOKとわかった(>>109)が、P, Q, (!P && !Q)
の3関数に振り分けたい場合にこの4条件を満たすようなのないですかね?

というのが質問です。ちゃんと書かずにすみません。コンパイラはgccです。

117デフォルトの名無しさん:2007/10/01(月) 05:47:44
>この4条件を満たすようなのないですかね

自分で書いた>>109が満たしてると思うんだが
118デフォルトの名無しさん:2007/10/01(月) 05:58:35
>>117
おっしゃる通りなんですが、>>109は、V==0やV==1という条件が
繰り返し登場してしまい、メンテナンス性がいまいちかなと思いまして。
実際はenumとか扱いたいので。

109の繰り返しになりますけど、条件1-4をみたし、かつdefault case

template<int V>
static void boo(typename boost::disable_if_c<V == 0 || V == 1>::type* = 0) {   /* default */ }

を綺麗にかけないですかね。

template<int V> static void boo(...) { /* default */ }

とかが通れば最高なのに。
119デフォルトの名無しさん:2007/10/01(月) 06:02:23
struct a_condition : mpl::bool_<...> {};
としてenable_ifに渡すとか
120デフォルトの名無しさん:2007/10/01(月) 09:08:09
kwsk
121デフォルトの名無しさん:2007/10/01(月) 09:54:53
引数忘れた
こんな感じ
enable_if< my_conditionA<V> >

まあディスパッチすべきだな
enable_ifはこの場合必要ないから
122デフォルトの名無しさん:2007/10/01(月) 11:56:27
デザパタのプロトタイプパターンを使ってみたいのですが
ばらばらに clone() 関数をとりつけるよりも
ひとつ Clonable クラスを作って、そのクラスから
継承したほうがよいでしょうか?
123デフォルトの名無しさん:2007/10/01(月) 12:34:46
そういう継承ってどうなんだろうね。
124デフォルトの名無しさん:2007/10/01(月) 17:41:51
noncopyableとかあるし、いいんじゃね?
125デフォルトの名無しさん:2007/10/01(月) 18:16:10
traitsを作れば継承はいらないと思うよ
126デフォルトの名無しさん:2007/10/02(火) 21:42:40
#include <boost/numeric/ublas/vector.hpp>
using namespace boost::numeric::ublas::inner_prod;

VC++2005EEの環境でビルドすると、
error C2867: 'boost::numeric::ublas::inner_prod' : は名前空間ではありません。
というエラーが出ます。
エラーの原因は何ですか?
127デフォルトの名無しさん:2007/10/02(火) 22:08:58
名前空間ではないものをusing namespaceしたこと
128126:2007/10/02(火) 23:00:22
>>127
http://sealsoft.jp/namespace.html このサイトの
> usingを使って、ある識別子をグローバルな名前空間に持ち上げることができる。こうするとその後は大域解決演算子を使う必要がない。
> using namespace seal::foo;
> // 関数fooを呼び出す
> int a = foo();

ここ見てできると思ったんですけど、このサイト間違ってますか?
129デフォルトの名無しさん:2007/10/02(火) 23:27:47
usingディレクティブ (using namespace)の対象にできるのは、名前空間だけ。
代わりといってはアレだが、その他の識別子一般には、using宣言が使える。
using boost::numeric::ublas::inner_prod;
130126:2007/10/02(火) 23:49:25
>> 129
なるほど、そうなんですか。

http://msdn2.microsoft.com/ja-jp/library/6f133eff(vs.80).aspx
ここを勘違いして見てました。(classの中のusingとは別物なんですね)

クラスの中でnamespace内の関数をusingしたい場合、
class A {
using boost::numeric::ublas::inner_prod;
};
エラーになってしまうのですが、クラス中でnamespace内の関数をusingするのは無理ということですか?
131デフォルトの名無しさん:2007/10/03(水) 00:09:31
そういうこと。クラス定義内のusingは基底クラスの名前を指定することに特化している。
なお、型名だけはtypedefで代用できる。
132126:2007/10/03(水) 00:14:05
ありがとうございました。
133デフォルトの名無しさん:2007/10/03(水) 01:54:49
マクロ使って、行数と引数を連結させたいのですが、

#define macro( name )\
const char *x = "name##__LINE__";

とかやってもできません。
こんなことは可能ですか?
134デフォルトの名無しさん:2007/10/03(水) 02:05:02
__LINE__は定数だからダブルクォーテーションで囲っちゃだめっしょ
で、定数を文字列にするのは単純なマクロじゃ厳しいと思うけど・・・
おとなしく関数にしたほうがよさそう
135デフォルトの名無しさん:2007/10/03(水) 02:07:38
一応マクロでこんな感じでいかが?
#define macro( buf, name ) sprintf( buf, "%s%d", "name", __LINE__);
136デフォルトの名無しさん:2007/10/03(水) 02:10:53
#define NUM2TEXT_(n)    #n
#define NUM2TEXT(n) NUM2TEXT_(n)

#define macro(name) \
const char *x = name ## NUM2TEXT(__LINE__)
137デフォルトの名無しさん:2007/10/03(水) 02:43:41
演算子オーバーロードって副作用完了点のことも考慮しないといけないんですか?
std::cout << "test" << std::endl;
で (a) "test" << std::endl; が先に評価されて、次に std::cout << (a) が評価される、という事態にはならないんですか?
138デフォルトの名無しさん:2007/10/03(水) 03:26:56
優先順位の同じ演算子の並びは左から評価じゃなかったのか
139デフォルトの名無しさん:2007/10/03(水) 04:07:20
左結合と右結合があってね・・・
140133:2007/10/03(水) 05:13:05
ありがとうございます。
>>136さんのは
どういう原理なんでしょうか?
141デフォルトの名無しさん:2007/10/03(水) 08:46:05
7**7**7 の下一桁の数字は?
142デフォルトの名無しさん:2007/10/03(水) 09:44:47
>>137
多重定義されている場合、通常の関数と同様、
呼出の直前に副作用完了点が現れるので心配は要らない。

<<は左結合だから、まずstd::cout << "test"から取り掛かる。
これは多重定義されているので、std::cout.operator <<("test")という関数呼出に相当。
関数呼出の直前には副作用完了点が来るので、ここまでにstd::coutと"test"が評価される。
と言っても、共に副作用を持たないので何も起きないが。
仮に副作用を持つ式だった場合、通常の関数呼出同様に
<<の左側と右側のどっちのオペランドが先に評価されるかは決まっていない。

std::cout.operator <<("test")の戻り値をrとすると、
次にr << std::endlの評価に掛かる。以下同じ。
143デフォルトの名無しさん:2007/10/03(水) 11:51:51
>>140
> 16.3.2 The # operator
> 16.3.3 The ## operator
144デフォルトの名無しさん:2007/10/03(水) 13:50:35
>>133
#define XY(X,Y) X##Y
#define MAKENAMEXY(FX,LINE) XY(FX,LINE)
#define MAKENAME(FX) MAKENAMEXY(FX,__LINE__)
というマクロで連結させている例がある。
評価順その他の関係で、間に一段置かないとならないらしい。
145デフォルトの名無しさん:2007/10/04(木) 00:31:45
VS2008EEで>>136が正常に動作しないんだけど・・・
コンパイラの仕様かな?
146デフォルトの名無しさん:2007/10/04(木) 00:36:58
プリプロセッサの仕様じゃね?とかつまんない事言うね。義務として。
147デフォルトの名無しさん:2007/10/04(木) 00:45:12
すみません。継承について質問です。

クラスBaseを基底とするクラスDerivAやクラスDerivBがあるとして、
そこからインスタンスを作成するとすると、

Base* pA = new DerivA;
Base* pB = new DerivB;

となると思います。
そこから、pAもしくはpBから新たなインスタンスpCを作りたいと思っているのですが、
どうしたらいいでしょうか?

単にpA(DerivA)だけであれば、DerivA *pC=*pAだけでいけるのですが、
pAとpB(最終的にはBaseを基底とするクラス全部)にも対応できるものを作りたいので、
どうか力をお貸しください。
148デフォルトの名無しさん:2007/10/04(木) 00:53:05
class Base {
public: virtual Base *NewInstance() = 0;
};
class DerivA : public Base {
public: virtual Base *NewInstance(){ return new DerivA; }
};
class DerivB : public Base {
public: virtual Base *NewInstance(){ return new DerivB; }
};

Base *pA = new DerivA;
Base *pB = new DerivB;
Base *pC = pA->NewInstance();
Base *pD = pB->NewInstance();
149デフォルトの名無しさん:2007/10/04(木) 00:53:41
Base* pA = new DerivA();
Base* pB = new DerivB();
150147:2007/10/04(木) 01:02:02
>>148、149
目からウロコが落ちました。

インスタンスを作成する関数を別途で作ればいいわけですね。
ありがとうございます。
151デフォルトの名無しさん:2007/10/04(木) 01:04:17
>>148
DerivA::NewInstanceはDerivA*を返し、
DerivB::NewInstanceはDerivB*を返し、
という具合に、そこは共変にしてほしいな。
152デフォルトの名無しさん:2007/10/04(木) 01:06:08
凶変を許したことでできるようになったことってなんだっけ?
なんかの本にかいてあったが忘れた
153デフォルトの名無しさん:2007/10/04(木) 01:15:57
>>136
boostにはなんて名前で入ってたっけ
154デフォルトの名無しさん:2007/10/04(木) 01:18:23
>>152
pAはDerivA*と分かっているとき、
DerivA* pA2 = static_cast<DerivA*>(pA->NewInstance());
のようなキャストを型安全性を損なうことなく排除できる。
155デフォルトの名無しさん:2007/10/04(木) 02:07:15
dynamic_castすれば共変なしでも安全じゃね?
156デフォルトの名無しさん:2007/10/04(木) 02:08:25
157デフォルトの名無しさん:2007/10/04(木) 02:29:39
>153
BOOST_PP_STRINGIZE
158デフォルトの名無しさん:2007/10/04(木) 08:19:17
これじゃだめなん?

Base *pC = new DerivC;
159デフォルトの名無しさん:2007/10/04(木) 08:20:10
Base *pC = new DerivC(pA);
Base *pC = new DerivC(pB);
160デフォルトの名無しさん:2007/10/04(木) 21:28:42
>>155
それだと余計な負荷がかかる。
161デフォルトの名無しさん:2007/10/05(金) 01:29:04
俺的c++開発環境構築メモ

目的:最終的にlinuxで動かせるようにしないといけないけどVisual Studio捨てれない

winxpにvmwareいれてゲストOSとしてubuntu7を入れる
ubuntuの/home/srcをsambaで共有できるようにしてホストOSのwinxpからみれるようにする

/home/src = \\ubuntu\src
の下にVisual Studioのプロジェクト作成

makefileはeclipse/CDTで自動生成

あとはemacsでメインのコードの編集するけど、flymakeとか使いつつ
インテリセンスも使えてeclipse/cdtのリファクタリング機能も使える環境のできあがり
162デフォルトの名無しさん:2007/10/05(金) 04:20:16
俺がいる
163デフォルトの名無しさん:2007/10/05(金) 08:18:16
もう遅いだろうがcoLinuxを薦めてみる
164デフォルトの名無しさん:2007/10/05(金) 12:27:41
coMomongaを勧めてみる
165デフォルトの名無しさん:2007/10/05(金) 12:59:49
coLinuxの方が便利なの?
速度が速い以外のメリットがないなら、もう乗り換えれない
166デフォルトの名無しさん:2007/10/05(金) 15:23:45
coLinuxってkernelのバージョンあがるたびに中身を全消ししないといけないって聞いたのだけど
違うの?
167デフォルトの名無しさん:2007/10/05(金) 17:36:55
ヘッダファイルなどで記述したグローバルなstatic変数は,
includeしたソースが複数ある(各ソースではincludeガードが起きずに展開される)
場合も単一の存在となるんでしょうか?
それとも別々の独立した変数となるんでしょうか?
168デフォルトの名無しさん:2007/10/05(金) 17:41:00
それをインクルードしたソースファイルごとに別々に作られることになる
169デフォルトの名無しさん:2007/10/05(金) 18:02:52
ありがとうございます.
あれ,でもクラス変数などは単一なんですよね?
うーむ,基本の理解が全然出来ていない.
170デフォルトの名無しさん:2007/10/05(金) 18:26:17
クラスの static 変数はどこかで1個だけ実体を定義する必要がある。

class A{
 static int x;
};
int A::x;  // <-- これ

2個以上のソースファイルで定義したら、定義が重複してるってリンクエラーになる。
static でない普通のグローバル変数と同じあつかい。
171デフォルトの名無しさん:2007/10/05(金) 20:36:51
#includeは単にファイルをくっつけてるものと考えれば理解しやすいかも
172デフォルトの名無しさん:2007/10/06(土) 00:19:53
>#includeは単にファイルをくっつけてるものと考えれば理解しやすいかも
くっつけるというのはちょっと違う。単にインクルードするだけ。
173デフォルトの名無しさん:2007/10/06(土) 03:48:00
>>169
ファイルスコープの static はクラスメンバやローカル変数の static とは全然
意味が違う。これは理解するとかじゃなくて覚えておく必要がある。
174デフォルトの名無しさん:2007/10/06(土) 12:08:54
C の仕様設計ミスとも言われている
175デフォルトの名無しさん:2007/10/06(土) 13:25:34
ここで聞いて良いか解りませんが
HTMLのtableタグを抜き出して2次元配列化するのに簡単な方法ありますか?
176デフォルトの名無しさん:2007/10/06(土) 13:38:01
簡単な方法かどうかわからんが、文字を読み込みながら解析していきゃいいんじゃね?
表の大きさがあらかじめ分かってるなら楽、わかってなくても確保すりゃできる。
177デフォルトの名無しさん:2007/10/06(土) 13:43:54
rowspanとかの扱いが面倒くさいなと(´Д`;)
178デフォルトの名無しさん:2007/10/06(土) 14:04:10
>>177
大丈夫、Lynx辺りのソースを見れば書いてあるはずだ。
# 簡単とは思えないが。
179デフォルトの名無しさん:2007/10/06(土) 19:44:49
100行くらいあるテーブルで
最後の行にだけ colspan 書いてあったり?
180デフォルトの名無しさん:2007/10/06(土) 19:55:07
それは困らんだろ
181デフォルトの名無しさん:2007/10/07(日) 22:00:29
Linuxでg++4.1.2を使ってるんですが、簡単なODR違反って、リンカが検出してくれたりしないんでしょうか?
182デフォルトの名無しさん:2007/10/08(月) 01:04:43
>>181
簡単なやつならシンボルの重複が発生してリンカのエラーになるよ。
183デフォルトの名無しさん:2007/10/08(月) 01:15:15
g++だと、クラステンプレートの中の関数はweak symbolになってしまうようで、
重複しても怒られないんだよね.....
184デフォルトの名無しさん:2007/10/08(月) 07:47:24
>>183 それは難しいやつってことで。
185デフォルトの名無しさん:2007/10/08(月) 14:08:29
最近C++やったのだけど
ただクラスを作って使うだけでもCよりは使いやすいよね、これ。
186デフォルトの名無しさん:2007/10/08(月) 14:10:02
クラスを作らないで使わないでもCよりは使いやすい
187デフォルトの名無しさん:2007/10/08(月) 14:12:06
C+関数オーバーロード+テンプレートで作ると意外と強力
188デフォルトの名無しさん:2007/10/08(月) 14:14:40
BOOST_PPだけで作ると読めない。
189デフォルトの名無しさん:2007/10/08(月) 14:21:37
>>185
関数型や今時のLLの真似をしようとすると
すぐに泣くことになるけどな
190デフォルトの名無しさん:2007/10/08(月) 14:55:31
BjarneStroustrup様に感謝しなさい。
191デフォルトの名無しさん:2007/10/08(月) 16:51:26
以下のコードがsegmentation faultで落ちます。

#include <boost/regex.hpp>

int main()
{
 boost::regex re("^(..)*\\xA4");
}

(ひらがなを含むEUCコードの文字列の正規表現)


コンパイル/実行環境:
i686, linux-2.6, gcc-4.1.2, boost-1.34.0, -O3オプション

ia64、-O2オプションでも試しましたが、その場合は問題は発生しませんでした。

私はこれ以上調べる知恵を持たないのですが、GCCのバグなのでしょうか?
192デフォルトの名無しさん:2007/10/08(月) 17:17:20
ICE? 実行時のSEGV?
boostのバグかもしれんよね。
193デフォルトの名無しさん:2007/10/08(月) 17:43:33
とりあえず core から stack trace を見るんだ
194191:2007/10/08(月) 18:07:48
GDBで覗いてみたら解決しました。
原因は恥ずかしくて言えません。あまりにも下らないミスでした。
スレを汚して申し訳ありません。
195デフォルトの名無しさん:2007/10/08(月) 21:55:59
いや、相談しに来たなら原因言ってから取り下げろって。
196デフォルトの名無しさん:2007/10/08(月) 22:02:02
>>194
恥ずかしがることないじゃないか、減るもんじゃなし。
このまま消えたらそれこそスレ汚し。質問に対して考えてくれた人に対して礼を欠く事になるぞ。
197デフォルトの名無しさん:2007/10/08(月) 22:17:26
おまえら恥ずかしい原因聞きたいだけだろと
198191:2007/10/09(火) 00:44:29
自分でインストールしたboostとシステムの管理者がインストールしたboostがあって、
後者の存在はこの問題を解決するまでは知りませんでした。

自分のboostを使うときは-lboost_regex-gcc41としなければならないのですが、
-lboost_regexと間違えていました。
管理者の用意したboostと何事もなくリンクしてしまうのでミスに気付かなかった。

GDBの出力に /usr/lib... という文字列を見つけて始めてミスに気付きました。



あれ? でもおかしいな。違うboostをリンクしたらそれはそれでうまく動くんじゃないんでしょうか?
199デフォルトの名無しさん:2007/10/09(火) 01:01:52
>>198
「違うboost」の何が違うのか調べないと、原因はわからんな。
200デフォルトの名無しさん:2007/10/09(火) 01:09:37
別に恥かしいことじゃなかったな。
しかし管理者か。
自分の視野外からバグが入り込むとはまるよな。
201デフォルトの名無しさん:2007/10/09(火) 01:29:34
boostって何者ですか? どっかの誰かによって拡張されたものですか?

標準ライブラリではないとは思うのだけど、それなら、
boostを使って記述すると、環境依存(バージョン依存)物とか言って怒る人います?
202デフォルトの名無しさん:2007/10/09(火) 01:32:43
怒る人がいるかどうかは、お前の環境依存。会社とか。 >>201
203デフォルトの名無しさん:2007/10/09(火) 02:15:23
>>198
原因は措いておくとして。
自分がスーパユーザじゃなくて自前でインストールした
ライブラリとかを利用するときは、-I でインクルードパスを明示するのと、
リンク時には -L でライブラリパスを明示するのを習慣付けておいたほうが
良いで。
204デフォルトの名無しさん:2007/10/09(火) 02:22:30
>>198 >>203
実行時のLD_LIBRARY_PATHも忘れずに。

それが面倒なら、boostの場合は、.soでなく.aのほうをリンクしてしまうのも手だ。
-lを使わず、/home/mona/lib/libboost_regex.a とフルパスを書いてしまう。
205デフォルトの名無しさん:2007/10/09(火) 12:33:32
boost/regexで日本語扱うにはユニコードに変換しないと駄目なんじゃないの?
206デフォルトの名無しさん:2007/10/09(火) 17:23:06
namespaceで区切ってグローバル関数を使うのと
クラスを作ってメンバ関数として使うのと

どちらがパフォーマンスがいいのだろうか?
207デフォルトの名無しさん:2007/10/09(火) 17:32:11
>>206
どちらも同じコンパイル単位内に関数の実体があると仮定していいなら、後者の方がインライン展開されやすいので
パフォーマンスが高い可能性がある。但し、コンパイラによっては全く同じになる可能性も高い。
208デフォルトの名無しさん:2007/10/09(火) 17:48:35
>>207
ありがとう!
つまり、ソースの読みやすさを優先すればいいって事ですね?
209デフォルトの名無しさん:2007/10/09(火) 19:04:01
パフォーマンスは置いといて、こういうのって、
(自分流でも)オブジェクト指向に沿って考えたら自然と決まるもんじゃないの?
それともC++のクラスってオブジェクト指向以外の用途も一般的?
210デフォルトの名無しさん:2007/10/09(火) 19:33:22
test
211デフォルトの名無しさん:2007/10/09(火) 19:45:35
testy
212デフォルトの名無しさん:2007/10/09(火) 19:51:39
testest
213デフォルトの名無しさん:2007/10/09(火) 20:02:24
>>209
構造化にしろオブジェクト指向にしろ、ソースのメンテナンス性を上げるための物だと理解してます
グローバルな関数にした方が使い勝手が良ければグローバル関数で処理するし
クラス化した方が使い勝手が良ければクラスを使います

使い勝手というのが、ある場面ではパフォーマンスであったり、ある場面ではメンテナンス性であったりするわけですが
また、メンテナンス性は、ソースの可読性に大きく左右されるので、パフォーマンスが同等であるならば、ソースの可読性を優先するのは自然だと思います
214デフォルトの名無しさん:2007/10/09(火) 20:42:41
namespace hage{namespace hoge{
  void func() {}
  }}

struct hage2 {struct hoge2 {
  static void func() {}
    };};

int main() {
  hage::hoge::func();
  hage2::hoge2::func();
}

どちらでも階層を実現できるけど
class struct を使う方法ならアクセス指定もできる
よって選らぶなら後者?…なわけないな
215デフォルトの名無しさん:2007/10/09(火) 20:44:08
×選らぶ
○選ぶ

らぶ
216デフォルトの名無しさん:2007/10/09(火) 20:48:47
>>213
なるほど、C++初心者だけどOOPに慣れてるから、まずOOがあるものとして考えてたよ
ただ、
> ソースの可読性を優先するのは自然
って考えた時に、オブジェクトとして捉えられる物はクラス化した方がいい場合があるのは当然として、
そうでないものをクラスにまとめることもあるのかな?ってのを疑問に思ったの

名前空間とクラスのどっちを選ぶかは目的の持っている意味で分けられて、
それで結果的に可読性が向上すると思ってるから
217デフォルトの名無しさん:2007/10/09(火) 23:08:42
char hoge[5000*5000];
とか書いといて走らせると、hogeがちゃんと確保されないんだけど、
これって当然なんでしょうか。
100*100とかだと大丈夫。
アクセスするとseg faultしちゃう。
newしてやるとちゃんと確保される。

gcc + Linux or OS X
218デフォルトの名無しさん:2007/10/09(火) 23:11:37
コンパイラでスタックの量を24MB以上許容してくれるように設定しなさい。
219デフォルトの名無しさん:2007/10/09(火) 23:22:40
>>218
ああ、そういうのがあるんですか。
newしてポインタがNULLかを調べるほうが普通?
220デフォルトの名無しさん:2007/10/09(火) 23:27:35
とりあえずスタックとヒープの違いについて調べるのが普通
221デフォルトの名無しさん:2007/10/09(火) 23:29:53
C++の規格にスタックとかヒープなんてあったっけ?
222デフォルトの名無しさん:2007/10/09(火) 23:31:53
ないね
223デフォルトの名無しさん:2007/10/09(火) 23:35:58
>>219 標準 C++ で、ただの new がヌルを返すことはありません。
224デフォルトの名無しさん:2007/10/10(水) 01:55:15
まぁ規格になくても知っといた方がいいやな。
225デフォルトの名無しさん:2007/10/10(水) 21:01:39
Javaでスタックにオブジェクトおくにはどうすればいいの?
もちろん、スレちがいだかんね。
226デフォルトの名無しさん:2007/10/10(水) 21:13:13
SomeClass *p = new SomeClass();

SomeClassのコンストラクタの処理が凄い思いとする。
この重い処理中、p は NULL? 非NULL? どちら??
処理系の実装依存なのかな。
227デフォルトの名無しさん:2007/10/10(水) 21:53:05
ごみ値。
228デフォルトの名無しさん:2007/10/10(水) 21:56:43
VC6やそれ以前を前提に話をしたいならそれ専用のスレに行ったほうがいい。
あれの動作は特殊だからねぇ〜
229デフォルトの名無しさん:2007/10/10(水) 22:01:04
スレチ杉てわらってしまった
230デフォルトの名無しさん:2007/10/11(木) 12:10:34
SomeClass *p = new(nowthrow) SomeClass();

ってやれば、一応失敗すればヌルポを返す
231デフォルトの名無しさん:2007/10/11(木) 13:19:46
そしてコンストラクタが例外を投げるとw
232デフォルトの名無しさん:2007/10/11(木) 15:03:47
>nowthrow
233デフォルトの名無しさん:2007/10/11(木) 18:40:50
いま投げる??
234デフォルトの名無しさん:2007/10/11(木) 19:52:03
ナウいな
235デフォルトの名無しさん:2007/10/11(木) 20:08:31
C++TESTって使ったことある人いる?

あれで構造体が「truncated」ってなって設定できないんだけど、何で?

教えてくださいエラい人。
236デフォルトの名無しさん:2007/10/11(木) 23:13:27
>>230
例外を使ったことない人が、例外を使いたくなくてひっかかる勘違いだな。
237デフォルトの名無しさん:2007/10/12(金) 05:59:42
ICUのUnicodeString
クラスのインスタンスの比較で
operator==
使ったんだけどおれは今まで
bool(最悪でもint)を想定してコードを書いてきたんだ。

そしたら、
返された型がUBool = signed char
だったんだ・・・
UBoolってboolっぽいから盲点だったよ。
pimplでラップしろとのお告げなのだろうか・・・

std::cout << o1 == o2 << std::endl;//で判明
238デフォルトの名無しさん:2007/10/12(金) 08:08:01
比較演算子はboolじゃなくてintが基準だよ。
239237:2007/10/12(金) 09:12:42
>>237
冗談かと思ったら散々な結果・・・
比較演算子の型は不明?w

std::cout << typeid(1.0==1.0).name() << std::endl;//VC6(int),VC7.1(int),VC8(bool),GCC3.4.4(bool)
std::cout << typeid(1==1).name() << std::endl; //VC6(long),VC7.1(bool),VC8(bool),GCC3.4.4(bool)

結論:boolは関数オーバーロードしない。または、明示的に呼び出す。
240デフォルトの名無しさん:2007/10/12(金) 09:22:22
>>239
これまじで?
もうVC6とかVC7.1は使わないから、いまさらどうでもいいんだけど。
241デフォルトの名無しさん:2007/10/12(金) 10:58:30
>>238-239
規格では組み込みの比較演算は全部 bool になる。
VC の比較演算か typeid がバグってるんだろ。
242デフォルトの名無しさん:2007/10/12(金) 18:07:19
#ifndef HOGE_H
#include "hoge.h"
#endif

と、hoge.h内で

#ifnedef HOGE_H
#define HOGE_H 1
class hoge{
};
#endif

ってするのはどっちにどういう長所短所があるんでしょうか。
243デフォルトの名無しさん:2007/10/12(金) 18:18:11
前者はISO-C以前のアナクロな手法。C++でそんなことやるのは馬鹿。
244デフォルトの名無しさん:2007/10/12(金) 18:22:11
>>243
あざっす。
数十種類の色んな環境でmakeできるソフト読んでたんで、
前者はそういうとこで念のために使う感じですね。
245デフォルトの名無しさん:2007/10/13(土) 15:06:26
>>242
コンパイル速度上げるための小細工。hoge.h の中で #ifndef してると、当然
hoge.h を読み込んでプリプロセッサが解析するコストがかかるが、前者だと
ファイル開く必要がない。

ちなみに #pragma once 使える環境なら、そっちの方が良い。
246デフォルトの名無しさん:2007/10/13(土) 15:27:50
#ifdef _MSC_VER
# pragma once
#else
# ifndef XXX_IS_INCLUDED
# define XXX_IS_INCLUDED
/* */
# endif
#endif

こうですか?わかりません><
247デフォルトの名無しさん:2007/10/13(土) 15:34:47
>>245
gcc は #pragma once 使わなくてもインクルードガードのパターンを認識して
同等の処理をしてくれるらしい。

つまり #pragma once しか使えない環境なら付けといたほうがいいかも、って感じ。
248デフォルトの名無しさん:2007/10/13(土) 17:35:03
>>246
未知の#pragmaは無視してくれるんじゃなかったっけ?
249デフォルトの名無しさん:2007/10/13(土) 17:44:39
まぁでも#pragma once に別の意味があるコンパイラもあるかもしれん
250デフォルトの名無しさん:2007/10/13(土) 17:45:42
>>248
コンパイラによっては同じ名前でも違う意味だったりする可能性もあるから
#pragma はたちが悪い。
251デフォルトの名無しさん:2007/10/13(土) 22:36:50
インクルガドのパターンは標準的だしそれでいいんじゃねーの
252デフォルトの名無しさん:2007/10/14(日) 04:02:26

void fh() {
 try {
  throw;
 } catch(int) {
  printf("1\n");
 } catch(bool) {
  printf("2\n");
 }
}

int main() {
 try {
  throw true;
 } catch (...) {
  fh();
 }
 return 1;
}

これってhack? これ許されるなら、TypeListの
要素全てをcatchするなんてのも出来そう。
253デフォルトの名無しさん:2007/10/14(日) 04:20:38
>>252
なにがうれしいのかよくわからん。kwsk.
254デフォルトの名無しさん:2007/10/14(日) 07:28:46
>252
ttp://www.parashift.com/c++-faq-lite/exceptions.html#faq-17.9
に idiom として載ってるくらい普通。

と、言っておきながらつい最近までこういうのが可能だと知らんかったけど。
255デフォルトの名無しさん:2007/10/14(日) 09:05:19
例外処理として使うならいいが、ダブルディスパッチ的に使うのは好かん
256デフォルトの名無しさん:2007/10/14(日) 10:42:59
> 254
C++つかってもう直ぐ10年だが初めて知ったorz

> 253
template <typename TL,typename T>
struct Catch {
 void do_catch() {
  try { throw ; } catch (T) {
   /*何か処理*/
  } catch (...) {
   Catch<mpl::pop_front<TK>::tyep,mpl::front<TL>::type>::do_catch();
  }
 }
};
こんな感じにすればTypeList全要素のcatchもできそう。
パフォーマンスわるそうだけど。
ほかにも工夫すればあれやこれが(うひひ
257デフォルトの名無しさん:2007/10/14(日) 11:04:08
例外のパフォーマンスが良ければ迷わず使うんだがな…。
あと、例外指定との相性もわかんねえし
258デフォルトの名無しさん:2007/10/14(日) 11:17:11
例外処理のやってはいけない利用法の代表だな
259デフォルトの名無しさん:2007/10/14(日) 15:55:41
そこまでするならRTTI使ったほうが良いと思うな。
260デフォルトの名無しさん:2007/10/14(日) 15:56:48
あ、そういう意味じゃなかったか。すまん
261デフォルトの名無しさん:2007/10/14(日) 16:03:25
262デフォルトの名無しさん:2007/10/14(日) 16:04:40
>>247
「パターンを認識」って具体的には何よ?あいまいすぎて水伝みたいだとオモタ
263デフォルトの名無しさん:2007/10/14(日) 16:08:42
>>262
ファイル内のコード全体が #ifdef で囲まれてて、その中の先頭で対応するマクロの定義が
ある、ってパターンを認識するんじゃないか?

gcc の話だから、確実なところが知りたいんなら実験してソース読んだほうがいいな。
264デフォルトの名無しさん:2007/10/14(日) 16:17:40
boost.waveでもインクルードガードパターンの認識してた気がする
265デフォルトの名無しさん:2007/10/14(日) 16:44:09
http://gcc.gnu.org/onlinedocs/gcc-4.2.2/cpp/Once_002dOnly-Headers.html#Once_002dOnly-Headers
ですね。二度目以降はファイルがopenされなくなるという最適化。
266デフォルトの名無しさん:2007/10/14(日) 18:08:28
VC++で#pragma onceに以降したのはインテリセンスやアウトラインで#defineされた名前も拾うようになったってのもあるだろうな
267デフォルトの名無しさん:2007/10/14(日) 21:39:57
Typelistの全キャッチして何かできるの?
268デフォルトの名無しさん:2007/10/14(日) 21:43:03
普通にmplのイテレータ使って回すんじゃだめなの?
269デフォルトの名無しさん:2007/10/15(月) 01:09:41
Exceptional C++ Styleの「汎用コールバック」のところに、こんなコードが乗ってるんですが、
callbackのoperator()をconstにしていい理由がよくわかりません。

A::foo()がconstではないのに、なぜoperator()はconstでいいんでしょうか?

struct A { void foo() /* const */ {} };

template <class T, void (T::*F)()> class callback {
public:
  callback(T& t) : object(t) {}
  void operator()() const { (object.*F)(); }
private:
  T& object;
};

int main() {
  A a;
  callback<A, &A::foo> cb(a);
  cb();
}

メンバ変数objectが、値でなく参照だから?
おしえてくださいませ。
270デフォルトの名無しさん:2007/10/15(月) 01:11:50
>>269 正解。ポインタでもいいよ。
271デフォルトの名無しさん:2007/10/15(月) 01:13:05
thisがconstでも、ポインタの指す先はconstにならないんだよな・・・
272269:2007/10/15(月) 01:15:58
ソウダッタノカ...
結構長いことC++もconstも使ってきたつもりだったけど、しらんかった。ありがとー
273デフォルトの名無しさん:2007/10/15(月) 01:43:28
じゃあconst性を保てるコールバックオブジェクトってできないの?
274デフォルトの名無しさん:2007/10/15(月) 01:46:45
callback(const T& t) : object(t) {}
とか
const T& object;
にすればいいだけでは?
275デフォルトの名無しさん:2007/10/15(月) 01:47:14
template <class T, void (T::*F)() const> class ccallback {
public:
  ccallback(T& t) : object(t) {}
(あとは一緒)

でも作って、そっち使えばいいんでない? >>273
276デフォルトの名無しさん:2007/10/15(月) 01:47:55
const性の定義が...
277デフォルトの名無しさん:2007/10/15(月) 20:26:42
クラスのオブジェクトのポインタからnewで配列を作ったとき、
それぞれにコンストラクタを作用させる方法ってありませんか?

class A{・・・};
int main(){
A* a;
a=new A[10]←ここでコンストラクタは使えない?
}

アホですいません
278デフォルトの名無しさん:2007/10/15(月) 20:59:43
>>277
new[]では、デフォルトコンストラクタしか呼べない。
ほかのコンストラクタを使いたければ、今はおとなしく
std::vector<>でpush_backするなどしかない。
279277:2007/10/15(月) 21:21:48
どうもありがとう
280デフォルトの名無しさん:2007/10/15(月) 23:09:10
a=new A(obj)[10];
なんて出来ないのか。

デフォルトコンストラクタしか呼べないのには
何かしらの理由あるの?
281デフォルトの名無しさん:2007/10/15(月) 23:42:17
規格の汎整数昇格のところ読んでるんだけど、
変換「できる」って書いてるんだよね。
つまり、変換するかどうかは処理系定義ってことなのか・・・。
うちの環境じゃその下の浮動小数点昇格が行われないみたいだし、
処理系定義臭いな・・・。
282デフォルトの名無しさん:2007/10/15(月) 23:49:52
>>280
うまい文法が思いつかなかったんじゃねーの。

A * p = static_cast<A *>( ::operator new (sizeof(A) * 10) ) ;
std::uninitialized_fill_n(p, 10, A(/*初期値*/) ) ;

A *iter = p ;
A * const end = &p[10] ;
for ( ; iter != end ; ++iter )
{ iter->~A() ; }
::operator delete(p) ;

うん、自分でやるのは、果てしなく面倒だな。
283デフォルトの名無しさん:2007/10/15(月) 23:54:23
>>280
現行の規格では無理だね。

文法としては↓で問題ないような気がするんだけど。どうなんだろ。
a = new A[10] { ... };
284デフォルトの名無しさん:2007/10/15(月) 23:57:51
>>281
実際にどこで汎整数昇格が実行されるべきかどうかが別途規定されている。
処理系定義じゃないよ。
285デフォルトの名無しさん:2007/10/16(火) 00:02:45
>>284
お、そうなのか。安心した・・・。
286デフォルトの名無しさん:2007/10/16(火) 00:11:25
浮動小数点昇格は 5.2.2p7 の可変個引数の所でしか出てこないから
ここでしか昇格は行われないという認識でいいのかな?

#include <iostream>
using namespace std;

void Hoge(float ) { cout << "float " << endl; }
void Hoge(double) { cout << "double" << endl; }

int main() {
Hoge(0.0f + 1.0f);
}

で float が出力されるのは別にいいというわけね?
287デフォルトの名無しさん:2007/10/16(火) 01:24:41
new int[10]();
は出来るのにな
288デフォルトの名無しさん:2007/10/16(火) 01:37:01
>>283
a = new A[size] { ... };

として、... にはどう書くよ?
289デフォルトの名無しさん:2007/10/16(火) 01:38:15
>>288
↓と同じでいいだろ。
A a[] = { ... };
290デフォルトの名無しさん:2007/10/16(火) 02:10:06
>>289
size が動的に決まる場合どうするのよ
291デフォルトの名無しさん:2007/10/16(火) 02:28:36
>>290
new する。
っていうか、それ初期化の話と関係ない。
292デフォルトの名無しさん:2007/10/16(火) 03:39:33
>>291
size の値によって { ... } の ... に書くべき要素の数が変わるじゃん。
293デフォルトの名無しさん:2007/10/16(火) 03:40:22
それ動的って言わない
294デフォルトの名無しさん:2007/10/16(火) 03:53:47
>>292
それ考えたら構文とか以前にコンパイルが必要な言語という時点で無理だね。


new しない配列と同じ制約のうえで初期化子が使えるって感じが考えられるかも、
もっと考えていったら、やっぱりやめようってことになるのかね?

禿が「組み込み配列なんか使うな」で済ませたことも考えられる。
あとは std::initializer_list にがんばってもらおう。
295デフォルトの名無しさん:2007/10/16(火) 04:23:51
>>293
new してるのに動的じゃない場合を考えるって何て矛盾。
296デフォルトの名無しさん:2007/10/16(火) 04:25:52
>>293
{ ... } を使う時点で動的じゃないっつーことだ。
297デフォルトの名無しさん:2007/10/16(火) 09:54:55
>>285
各演算子のとこに書いてあるよ。
たとえば + は両オペランドに通常の算術型変換を施すけど、>>はしない。とかがわかる。
298デフォルトの名無しさん:2007/10/16(火) 12:43:03
人の作ったやつんなんだけど、豪快にメモリリークしてる。。

初心者の漏れはどやって調べればいいんだああ
299デフォルトの名無しさん:2007/10/16(火) 12:45:26
>>298
リークしていることが確実なのならば、全てのmalloc()/newからのロジックを追えばいい。
300デフォルトの名無しさん:2007/10/16(火) 13:07:49
>>298
_CrtSetBreakAlloc();
301デフォルトの名無しさん:2007/10/16(火) 13:16:00
>>300
井の中の蛙乙
302300:2007/10/16(火) 13:43:46
>301
うぜー

じゃあ
boundschecker
valgrind
で満足したか?
303デフォルトの名無しさん:2007/10/16(火) 13:44:50
>>302
恥の上塗り乙
304デフォルトの名無しさん:2007/10/16(火) 13:48:39
>>300=302
環境依存スレじゃないんだから、環境依存の手法をいくら提示してもダメでしょ。
まして、>298は環境を明示していないんだから。

>>298
つーことで、愚痴じゃないなら該当スレでどうぞ。その節は環境を明示することをお忘れなく。
つーか、該当環境スレで聞いたほうが早いかな。
305デフォルトの名無しさん:2007/10/16(火) 14:45:09
でも「井の中の蛙」は意味違うよな。
306デフォルトの名無しさん:2007/10/16(火) 15:09:30
>>305
Windows環境の知識しかないなら、あってんじゃないの?
尤も、>300は>302で井の中のみならず多少の外界の知識もあることを披露している訳だが。
因みに、「井の中の蛙」と言った場合、通常は「井の中の蛙、大海を知らず」と言う意味で使う。
更に「されで空の青さを知る」などと付け加えてしまうのは無粋と言うものだと思う。
まぁ実際、>302で「うぜー」とか「満足したか」なんて言っているようではやはり、>300は井の中の蛙だと思うんだ。
307デフォルトの名無しさん:2007/10/16(火) 15:10:09
一字訂正
s/されで/されど/
308デフォルトの名無しさん:2007/10/16(火) 15:16:10
豪快にメモリリークしているなら、環境依存ではなく調べる方法。
適当にダンプしてみる。
もし、普通に使うメモリが数十MBなのに、数百MBも使っているとすれば、
かなりの確率で、リークしているメモリをダンプすることが出来る。
あとは特徴的なビット列なり、なんなりで、何のメモリかを特定すればよい。
309デフォルトの名無しさん:2007/10/16(火) 15:16:12
どっちも必死なのは分かったからどっちも消えろよ
310デフォルトの名無しさん:2007/10/16(火) 15:36:22
自分では自分のことを「おりこうさん」だと思っているのだろうから、
たぶんこの辺りからがしつこいと思うよ。
311300:2007/10/16(火) 16:05:08
いや俺は302以降発言してねーよ。勝手に必死認定すんな。
312デフォルトの名無しさん:2007/10/16(火) 16:59:19
>>311
やっぱ必死だなw
313デフォルトの名無しさん:2007/10/16(火) 17:47:13
>>311
やっぱ必死だなw
314デフォルトの名無しさん:2007/10/16(火) 20:19:12
コマンドライン等から
x*x+5*x+10+sin(x)
のような関数を読み込んで、
この関数を実行時に作成するような方法ってありますか。

double func(double x){
return x*x+5*x+10+sin(x);
}
↑こんなイメージの関数を実行時に作りたいと考えてます。

文字列を式として認識するようなこと自体難しいと思いますが、
それを仮にクリアしたとして、
とにかく引数を与えたときにその式の値を得る方法を知りたいです。

いい方法をご存知の方がいたら、ご教授いただきたく。
315デフォルトの名無しさん:2007/10/16(火) 20:24:59
>>314
tccというコンパイラのライブラリを使うと実行時に文字列からコンパイルできる。
316デフォルトの名無しさん:2007/10/16(火) 20:29:18
317デフォルトの名無しさん:2007/10/16(火) 20:38:21
C++ならboost.spirit
web検索かければサンプルコードも沢山あるから
比較的楽に実装できると思うよ
318デフォルトの名無しさん:2007/10/16(火) 20:48:30
ファイルに書き出してコンパイラを呼び出してDLL的なものにしてロードして実行。
319314:2007/10/16(火) 21:12:53
>>315-318
こんな短時間に色々ありがとう。
とりあえず、試してみます。

この前boost入れたんで、まずspiritっての使ってみようかと。


しかし上記のアルゴリズムを自分で書こうとしたらどうなるのか気になりますね。
320デフォルトの名無しさん:2007/10/16(火) 21:15:02
結局インタプリタを作るハメになるだけ
321デフォルトの名無しさん:2007/10/16(火) 21:15:18
322デフォルトの名無しさん:2007/10/16(火) 21:38:54
》319

トークン解析してひたすら関数オブジェクトを合成するような感じでしょう。きっと…
インタプリタなら関数(オブジェクト)になんかしなくていいわけですし…
323デフォルトの名無しさん:2007/10/17(水) 01:24:38
>319
自作するならPEGがお勧め。
結局spiritだけどな
324デフォルトの名無しさん:2007/10/17(水) 09:20:12
>>314
#include </dev/tty>
325デフォルトの名無しさん:2007/10/17(水) 13:18:21
私ゃawkを使ったけどね。
326デフォルトの名無しさん:2007/10/17(水) 17:27:41
質問失礼いたします。
引数付きのオブジェクト型の配列についてなのですが

Object **obj = new Object*[N];
for( int n = 0; n < N; n++ )
obj[n] = new Object( 0 );

こんなんがweb上に乗ってたんですが、
オブジェクト型の配列の添え字数分コンストラクタを呼びたいとき
もっと簡単の書き方はありますでしょうか?
327326:2007/10/17(水) 17:28:59
もっと簡単'な'でしたm(__)m
328デフォルトの名無しさん:2007/10/17(水) 21:11:44
レベルが低い質問かもしれません。
C++で割り込み処理(ex.ctrl+Dが入力されるまで永遠ループ)はできますか?
c=getchar() != EOF とかですと毎回止まってしまうので駄目です。

「C++ 割り込み処理」などでぐぐりましたが、ちょっとわかりませんでした。
CUIでやりたいのでVC++のみで可能ですと終わります。。
329デフォルトの名無しさん:2007/10/17(水) 21:19:28
標準ライブラリの範囲では無理。
330デフォルトの名無しさん:2007/10/17(水) 21:37:13
今ググってみたら
signalって標準だったのか・・・
331デフォルトの名無しさん:2007/10/17(水) 22:09:45
C++で文字列からそのクラスを作るのはできないですか?

class base{};
class super1:public base{};
class super2:public base{};

という風になっていて

base *s1 = getClass("super1");  // base *s1 = new super1(); と等価
base *s2 = getClass("super2");  // base *s2 = new super2(); と等価

ってのをやりたいです

事前にこんなので登録して、ここから呼び出したいのですが…
なにかうまい方法は無いでしょうか

map<string, ???> classmap;
classmap["super1"] = super1;
classmap["super2"] = super2;
332デフォルトの名無しさん:2007/10/17(水) 22:17:16
>329,330
ありがとうございます。同一の方ですか?
signalを調べてみようと思います!
333デフォルトの名無しさん:2007/10/17(水) 22:18:38
C++にはリフレクションがないので・・
334デフォルトの名無しさん:2007/10/17(水) 22:25:55
>>331
関数ポインタでも使ってみる?
class derived1;
base* create_derived1(){return new derived1();}

class derived2;
base* create_derived1(){return new derived2();}

map<string,base* (*)()> classmap;
classmap["derived1"] = create_derived1;
classmap["derived2"] = create_derived2;
335sage:2007/10/17(水) 22:31:24
>333
だ、だめか・・・
すいません。ありがとうございます!
336デフォルトの名無しさん:2007/10/17(水) 23:03:44
keyとなる文字列とクラス名がある程度一致してるならboost.preprocessorとanyでなんとかできるかもしれない
337デフォルトの名無しさん:2007/10/18(木) 00:06:30
C++ド初心者ですが
vector<int>のイテレータを
vector<int>::iterator p = .....;
と記述してるのですが、なんで、vector<int>::としなければならないのですか?
自分としては、なんとなく(iteratorがclassなら)
iterator< vector<int> > p = ....
と記述するのが普通じゃないのかと思うのですが

338デフォルトの名無しさん:2007/10/18(木) 00:08:41
iterator はクラスとは限らないからねぇ
単なるポインタの typedef ということもありうる
339デフォルトの名無しさん:2007/10/18(木) 00:27:50
boost::range_iterator<std::vector<int> >::type
なんてお呼びでない。
340デフォルトの名無しさん:2007/10/18(木) 02:17:06
vector<int>のクラス内でかかれているiteratorというクラスを使いたいから

vector<int>::iteratorがint*な実装がある。BCCがそうだし…
でもlist<int>::iteratorはまた別物で
list<int>の内部構造にあわせたクラスにしてある。

大事なのはiteratorという同じ型を使うのではなくて
iteratorという型を通して同じように要素を操作できることだから…。

型名::型名 が分らないのならば
vector<int>::iterator の vector<int> はコンテナクラスの型であると同時に
名前空間名でもあります。
クラスの名前空間とかインナークラスで探せば説明サイトが見つかると思う。
341デフォルトの名無しさん:2007/10/18(木) 02:21:17
>>334
それも考えたんですけど、100個ぐらいあるから関数を作るのが面倒なので…
boost使って自動化できたり出来ないですかね…
342デフォルトの名無しさん:2007/10/18(木) 07:20:06
>>341
boost::function, boost::lambda::constructor を組み合わせれば、道が開けるかも。
343デフォルトの名無しさん:2007/10/18(木) 07:22:22
>>326
どこが難しいと思ってるの?
344326:2007/10/18(木) 11:05:17
>>343
すみません、3行目は
obj[n] = new Object( n ); でした。

理解していないわけではないのですが、
ただ単にオブジェクト型の配列として定義したときに
カウンタとして用いているnをコンストラクタの
引数として用いたいのです。できればnewを用いずに。
配列宣言で引数付きコンストラクタを呼び出すことは
できないのでしょうか?
レベルが低くて申し訳ありませんm(__)m
345デフォルトの名無しさん:2007/10/18(木) 11:47:55
>>344
Object がコピーコンストラクタでコピーできるクラスなら。

std::vector<Object> obj;
for( int n = 0; n < N; n++ )
obj.push_back( Object( n ) );

これなら delete も要らなくて簡単。
346デフォルトの名無しさん:2007/10/18(木) 11:52:27
C++0xを待つんだな。
347326:2007/10/18(木) 11:53:56
>>345
早いご回答ありがとうございます!
やってみます!
348デフォルトの名無しさん:2007/10/18(木) 12:26:05
コピーでOKなら
std::vector<Object> obj( N, Object(n) );
349デフォルトの名無しさん:2007/10/18(木) 12:31:27
>>348 コンパイルエラー。
3507=9:2007/10/18(木) 14:25:42
>>349

Objectにコピーコンストラクタがあるなら大丈夫だと思うのだが…
(N回コピーコンストラクタが呼ばれる)
351デフォルトの名無しさん:2007/10/18(木) 14:26:32
コンストラクタをメモ化したい
352デフォルトの名無しさん:2007/10/18(木) 20:22:31
>>341
template<class T> base* create_derived(){return new T;}

classmap["derived1"] = create_derived<derived1>;
classmap["derived2"] = create_derived<derived2>;

boostなんて必要ないですね…orz...
353デフォルトの名無しさん:2007/10/18(木) 22:10:19
>352
#define REG(name) classmap[ #name ] = create_derived<name>
までやれば最強?
354デフォルトの名無しさん:2007/10/19(金) 00:39:31
現在ゲームで使うベクトル構造体を作っています。
struct Vec3
{
union {
struct {
float x;
float y;
float z;
};
float v[3];
};
// オペレータ群
・・・・
};

これを、

Vec3 v0, v1;
v0.xy = 1.0f;
v1.xyz = 1.0f
v0.xz = v1.zx;
みたいな使い方をしたいのですがどのようにすればいいのでしょうか?
よろしくお願いします。
355デフォルトの名無しさん:2007/10/19(金) 01:33:31
とりあえず代入する必要なところだけ。もっと面白いことも出来るだろうけど、ここに書くには余白が足りない。

struct proxy
{
 float & r1 ; float & r2 ;
public :
 proxy(float &r1, float & r2)
  : r1(r1), r2(r2) { }
 proxy(proxy const & p)
  : r1(p.r1), r2(p.r2) {}
 proxy const & operator = (float f) const
 {
  r1 = f ; r2 = f ;
  return *this ;
 }
} ;
struct Vec3
{
 float v[3] ;
public :
 proxy xy(void)
 { return proxy(v[0], v[1]) ; }
 proxy xz(void)
 { return proxy(v[0], v[2]) ; }
 proxy yz(void)
 { return proxy(v[1], v[2]) ; }
} ;

int main()
{ Vec3 v ; v.xy() = 1.0f ; v.xz() = 1.0f ; v.yz() = 1.0f }
356デフォルトの名無しさん:2007/10/19(金) 02:07:47
>>355
ありがとうございます。
参考にしていろいろ弄ってみます。
357デフォルトの名無しさん:2007/10/19(金) 02:40:44
>>354
とりあえず作ってみた。これで「v0.xz = v1.zx;」のような表記ができるよ。
完全にするにはSxy,Syz,Szx,Sxz,Szy,Szx,Sxyzの実装を網羅する必要がある。

struct Sxyz {
 float x,y,z;
 Sxyz & operator = (float f) { x=y=z=f; return *this; }
};
struct Sxy;
struct Sxz;
struct Szx;

struct Sxy : public Sxyz
{
 Sxy & operator = (float f) { x=y=f; return *this; }
};
struct Sxz : public Sxyz
{
 Sxz & operator = (Szx r);
};
struct Szx : public Sxyz {};

Sxz & Sxz::operator = (Szx r) { x=r.x; z=r.z; return *this; }

// つづく
358357:2007/10/19(金) 02:42:19
// つづき

struct Vec3
{
  union {
  struct {
   float x, y, z;
  };
  float v[3];
  Sxy xy;
  Sxz xz;
  Szx zx;
  Sxyz xyz;
 };
 Vec3() : x(0.0f), y(0.0f), z(0.0f) {}
 Vec3(float _x, float _y, float _z) : x(_x), y(_y), z(_z) {}
};

int main()
{
 Vec3 v0, v1;
 v0.x = 1.0f;
 v0.xy = 2.5f;
 v1.xyz = 4.0f;
 v0.xz = v1.zx;
}
359デフォルトの名無しさん:2007/10/19(金) 02:59:16
やべ、本当に>>355の要求した文法通りだ。
この発想はなかった。

でもunionってこんなことできるのかなと調べてみたら、やっぱり規格違反だった。
unionのメンバにクラスは使えるんだけど……。

>An object of a class with a non-trivial constructor (12.1), a non-trivial copy constructor (12.8), a non-trivial destructor
>(12.4), or a non-trivial copy assignment operator (13.5.3, 12.8) cannot be a member of a union, nor can an
>array of such objects.

というか、union自体がメンバ関数とか、コンストラクタやデストラクタ持てたんだ。
規格読んで今初めて知ったよ。
360357:2007/10/19(金) 03:00:30
もし v0.xyz = v0.zxy なんてことまでやろうとしたら、組み合わせの数がとんでもないことになるね。
361359:2007/10/19(金) 03:09:28
あ、間違えた。copy assignment operatorだったorz
疲れてるみたいだ。もう寝よう。
362デフォルトの名無しさん:2007/10/19(金) 03:11:37
>>357
おおっ!私のやりたかったことできるみたいですね!
参考にさせていただきます。ありがとうございます。
363357:2007/10/19(金) 04:04:00
>>354
すまん、訂正です。
「v0.xz = v1.zx;」はv0.x=v1.z, v0.z=v1.xという意味だろうから、以下のように直して。
(ついでに引数はconst参照の方がいいと思うので。)

Sxz & Sxz::operator = (const Szx &r) { x=r.z; z=r.x; return *this; }

>>359, 361
>でもunionってこんなことできるのかなと調べてみたら、やっぱり規格違反だった。
>>An object of a class with a non-trivial constructor (12.1), a non-trivial copy constructor (12.8), a non-trivial destructor
>>(12.4), or a non-trivial copy assignment operator (13.5.3, 12.8) cannot be a member of a union, nor can an
>>array of such objects.

>あ、間違えた。copy assignment operatorだったorz

面白そうだから作ってはみたけど、実は規格とか良く理解せずにいました。

non-trivial copy assignment operator というのはコピー代入演算子ということで
Sxz & Sxz::operator = (Sxz) ということでしょうか。
Sxz & Sxz::operator = (Szx) ならば問題なしという認識であっていますか?
364デフォルトの名無しさん:2007/10/19(金) 05:20:01
>>350 n が宣言されてない。 >344 のやりたかったこととたぶんちがう。
365デフォルトの名無しさん:2007/10/19(金) 06:38:10
だからなに。
366デフォルトの名無しさん:2007/10/19(金) 08:10:57
みっちゃん と入力しても みっちゃん が見つかりません。比較関数の書き方を教えて下さい。
#include <iostream>
#include <map>
#include <string>
class human{
private:
  std::string name;
  int age;
public:
  human(std::string name, int age){ this->name=name; this->age=age; }
  int getAge(void){ return age; }
  std::string getName(void){ return name; }
};

typedef std::map< char* , human > clsmap_t;

int main(void){
  clsmap_t clsmap;
  human yosida("吉田", 21), mitui("三井", 20);
  char buf[100];

  clsmap.insert(clsmap_t::value_type("よっちゃん", yosida));
  clsmap.insert(clsmap_t::value_type("みっちゃん", mitui));

  std::cout << "あだ名を入力して下さい : ";
  std::cin.getline(buf, sizeof(buf));

  clsmap_t::iterator n = clsmap.find(buf);
  if( n == clsmap.end() ) std::cout << buf << " not found." << std::endl;
  else std::cout << n->second.getName() << " " << n->second.getAge() << std::endl;
  return 0;
}
367デフォルトの名無しさん:2007/10/19(金) 08:19:58
368デフォルトの名無しさん:2007/10/19(金) 08:28:36
bufをstringに入れて、そのstringでfindかけてみてはどうだろう
369デフォルトの名無しさん:2007/10/19(金) 08:34:24
mapのキーもstringね
ってマルチかよ
370デフォルトの名無しさん:2007/10/20(土) 10:31:32
スタティックなメンバ関数と
friendな関数

どう使い分けたらいい?
371デフォルトの名無しさん:2007/10/20(土) 10:53:03
static 性的
friend 友達
372デフォルトの名無しさん:2007/10/20(土) 11:22:26
>>371
だれがうまいこと(ry
373デフォルトの名無しさん:2007/10/20(土) 11:31:07
>>370
C++3rdでは、friend、static、無印、の3つのメンバ関数を、こう分類してる。

メンバ関数の特性には次の3つがあって、
(1) 関数がクラス宣言の非公開部にアクセスできること
(2) 関数がクラススコープに含まれること
(3) オブジェクトを対象として関数を実行しなければならないこと(thisポインタを持っていること)
無印は(1)〜(3)、staticは(1)〜(2)、friendは(1)だけを持っている。

だから使い分けを考える時も、ここから出発するのがいいんではないかと。
どーしても(3)で困るならstatic、さらにどーしても(2)で困るならfriend、みたいな。
まぁ俺だったら、friendはよほどのことが無い限り使わないけど・・・。
374デフォルトの名無しさん:2007/10/20(土) 11:42:06
>>373
トンクス!
375デフォルトの名無しさん:2007/10/20(土) 11:54:56
(3)ということは
void Class::Delete()
{
 delete this;
}
は禁則事項?
376デフォルトの名無しさん:2007/10/20(土) 11:56:46
ごみん読み違いだったw
377337:2007/10/20(土) 13:21:52
>>338, >>340 トンクス
相変わらずよく分からずですが、そのクラスで用いるiteratorを
typedefでクラス内で定義しているのからだろう程度の理解で、C++の勉強を
先に進めるこすますた。
378デフォルトの名無しさん:2007/10/20(土) 13:32:22
そこでboost::range_iteratorとtypeof_の組みあわせ技ですよ
std::vector<int> v;
boost::range_iterator<BOOST_TYPEOF(v)>::type iter;
379337:2007/10/20(土) 15:11:20
STLすら解らないのに、boostなんて、><
boost::range_iterator<BOOST_TYPEOF(v)>::type iter;
のtypeもやっぱtypedefされてるから
boost::range_iterator<BOOST_TYPEOF(v)>::が付くのですか?
380デフォルトの名無しさん:2007/10/20(土) 15:48:49
>>379
それがboost::range_iterator<>の中で宣言された物だから。
typedefされたものかどうかは問題ではない。クラスや関数やその他いろいろなものでも同じ。
381デフォルトの名無しさん:2007/10/20(土) 16:25:20
実を言うと、宣言、定義が何なのかも解らないのです><
だから>>380の意味が解りません><,orz
382380:2007/10/20(土) 16:35:59
>>381
氏ね
383デフォルトの名無しさん:2007/10/20(土) 16:42:24
バカ同士仲良くしろよ
384デフォルトの名無しさん:2007/10/20(土) 16:43:08
>>383
自作自演乙
385デフォルトの名無しさん:2007/10/20(土) 16:53:49
>>383
バカじゃないのなら(頭良いなら、サクッと)
宣言、定義の解説汁
386デフォルトの名無しさん:2007/10/20(土) 16:57:14
387デフォルトの名無しさん:2007/10/20(土) 17:04:38
取りあえず、痔スレが立ったので
この相談スレは終了です。
*************** 相談スレ 終了 ***************

これよりC++雑談スレになります
C++談話室 part1
388デフォルトの名無しさん:2007/10/20(土) 17:06:21
何がしたいんだよ
389380:2007/10/20(土) 18:35:29
どうでもいいことだけど、382は俺じゃないよ。
2chで初めて騙られたw

まあ381はへこまずに、基本をちゃんと勉強すべきだ。
とりあえず宣言や定義について書いてある入門書くらいは読むこと。
390デフォルトの名無しさん:2007/10/20(土) 20:42:38
質問なんですが、ある特定の型だけ使える new のオーバーロードって定義できますか?

391デフォルトの名無しさん:2007/10/20(土) 20:46:53
その型がクラスなら、クラスの中に書けばそれが使われる
class X {
public:
void *operator new(size_t n);
void operator delete(void *p);
};
392デフォルトの名無しさん:2007/10/20(土) 23:29:25
すいません。先月から開発の部署に配属されまして、C++の習得が必要になったのですが、
ただの事務職の経験しかなく、勉強しはじめたものの、正直申し上げてさっぱりわかりません。

みなさんはどうやってだんだんと使えるようになっていきましたか?
コツコツと努力が必要なのは重々承知しておりますが、
努力の方向を誤らないよう、先人のたどった道がどんなものかを教えていただければと思います。
393デフォルトの名無しさん:2007/10/20(土) 23:51:21
こういう質問って、好きで始めた人間には答えづらいね。
俺の場合、少なくとも初期の頃は、本を読んで、ソースを書いて、何か疑問を持ったらネットで調べる、
というのを、その時その時の好奇心のままに続けてきただけだから、
教えるべき「道」なんてものがあるのかどうか、そこからしてわからない。
「握力を鍛えるにはどうすればいいですか?」→「何か握ってれば?」くらいシンプルな問答に思える。

嫌々この道に入らざるを得なかった人の回答を待ったほうがいいね。
394デフォルトの名無しさん:2007/10/21(日) 00:00:08
>>392
金とって開発してる組織でそんなことしてたらほとんど詐欺だな。
395390:2007/10/21(日) 00:01:28
>>391
ありがとうございます。早速試してみます。
396デフォルトの名無しさん:2007/10/21(日) 00:02:38
Accelerated C++とEffective C++だな
それとSTLを一通り使えるようにしとけば、まぁ問題ないだろ
そこからexceptionalとかいってもまぁ一般的な理系学部卒程度の素養があれば半年もかからないさ
397デフォルトの名無しさん:2007/10/21(日) 00:07:31
仕事だから勉強にいくらでも時間をかけられるということはないだろうけど、
基礎はしっかり身につけたほうがいいだろうね。

まずは入門書を読みながら、実際に書いて動かすこと。
読んで理解したつもりになってるだけでは、実際はほとんど身についていない。
書いてあるままを試して終わりにするのではなく、新しく習ったこれについて
こう変えてみたらどうなるか、などいろいろ試してみること。
本を写したつもりでもきっとどこか間違えるから、コンパイルエラーとか動作がおかしいということが
発生するだろうから、それを解決することで何が間違いかを学んでいくこと。

独学だと問題に行き詰ったときに大変だから、誰か身近に教えてくれる人がいると良いね。

業務でやるんだから、先輩とかに聞けば教えてくれるはず。
…その先輩が平均程度には良心とか責任感があるなら。
398デフォルトの名無しさん:2007/10/21(日) 00:08:50
そもそも半年も猶予があるのかという

それに、プログラミングは合わない人は全く習得できないからなあ
399デフォルトの名無しさん:2007/10/21(日) 00:10:07
>>392
好きでやろうが嫌々やろうがやることは一緒じゃないかな。
適当な入門書から入って真似して試して考えて調べて、、、

初心者にアドバイスしたいことは、
情報源は複数持つこと。一人の言うことを鵜呑みにせず、本やnetも並用すること。
何かに取り組むとき、現在の知識だけで何とかしようとするな。きっとより良い解決方法がある。
理解するまでは使うな。たまたま動いただけかも知れぬ。
400デフォルトの名無しさん:2007/10/21(日) 00:21:58
C++ Coding Standardは……ちょっと微妙かな。
趣味でC++やる/エキスパートを目指すなら必須だと思うけど。
401デフォルトの名無しさん:2007/10/21(日) 00:23:50
分からなかったときがあれば昼でも人がいるVipのプログラムスレお勧めw
402デフォルトの名無しさん:2007/10/21(日) 00:30:29
業務でプログラミングするときは、理想と現実の違いを受け入れることも大切。

勉強していくうちに、単に正しく動くものが書けるというだけではなく、保守性だとか
論理的な正しさとかに気を配るようになったり、自分なりのより良いと思えるスタイルができてくる。
でも職場ではそこ独自の理解しがたいルールがあることが多い。

悪い点を指摘して改善するように提案することも効果がある場合もあるけど、
変に我を通さずに協調する(受け入れる・理解する・妥協する)ことも必要。
403392:2007/10/21(日) 00:56:56
みなさんのお言葉感謝します。
とりあえずまともにレスできるところにだけ・・・・

>>393
なるほど、元々のアプローチが違いますからね。
聞かれても困ってしまうかもしれません。

>>394
全くです。金もらってこんなことしてるので、会社に居辛いです。

>>396
学部も文系、職種も文系で、C++に更に種類があることも存じませんでした。

>>397
基礎からみっちりと身につけるつもりでいます。
ただまあ、仕事は待ってくれないという問題はたしかにございます。

今ぶつかっている問題は、例えば、
「参考書のAの項目とBの項目は理解できました。」
「じゃあAとBを組み合わせて使ってください」 → ( ゚д゚ )
という、初歩の部分でも応用が全くできないというところです。
404392:2007/10/21(日) 00:58:35
>>398
なんだか入社時の適性ではプログラマ寄りの適性だったらしいのですが、
変数の概念が理解できない時点で色々とダメな気がします。

>>399
なるほど、情報源を複数持つことですね。
今は黙々と入門書とにらめっこしている状態ですが、
入門書を真似する>試す>わからないところが出てくる>考える>やっぱりわからない>調べる>何をどうやって?
でもって、周囲は待ってはくれないので、「そういう風に動くもんなんだ」と自分を納得させてます。

>>402
困ったことに理想を持つ前に、来月自分の机がそこにあるかという現実がありました。
通そうとする我すらありません。
405デフォルトの名無しさん:2007/10/21(日) 01:00:51
Accelerated C++ も Effective C++ も Exceptional C++ も本の名前
そういう種類の C++ があるわけじゃない
どれも、まだ C++ がさっぱりわからない状態では読む本じゃないな
406デフォルトの名無しさん:2007/10/21(日) 01:07:50
ほんとに何も知らない人に
Accelerated/Effective/Exceptional C++ 進める奴とか結構いるけどさ
どう考えたって間違ってるだろ
407デフォルトの名無しさん:2007/10/21(日) 01:11:18
>>403
ちゃうw
Accelerated C++とEffective C++はC++の種類じゃなくて本ね。
特に、Effective C++はC++使ってるなら知らないとモグリだと言われるくらいの本なので、
いつか辿り付くといいね。
初心者にはちときつい。
408デフォルトの名無しさん:2007/10/21(日) 01:21:48
>>403
世のため人のためこのスレのため、仕事を断れ。
409デフォルトの名無しさん:2007/10/21(日) 02:16:14
いきなりc++はきついやろ
できるならjava方面にしてもらえよ
つかそれって肩たたきなんじゃねえの
410デフォルトの名無しさん:2007/10/21(日) 04:06:00
皆さん、わて、Accelerated C++ とEffective C++ はじめてしました。
Effective C++ って第2版と第3版有るのですが、買うならやっぱり第3版のほう?
あと、C++の趣味グラマーにお薦めの入門書の次に読む本って何かある?
411デフォルトの名無しさん:2007/10/21(日) 09:23:26
>>410
自分も最近始めたC++趣味グラマーだが、C++ Primer 第4版を読んでる。

分厚いけど結構おすすめ。他の入門書よりかなり詳しく書かれているから。
1冊目としてはおすすめできないけど。2冊目にはいい。

特にAccelerated C++を読んだ人にはおすすめ。著者も一部共通しているし、
クラスの書き方からではなく、使い方から学んでいくという方針も共通している。

自分もAccelerated C++の後にこれを読み始めた。
今はちょうどPart Iを読み終えたところ。
ここまででやっと300ページ。あと残りページ600ページほど。
412デフォルトの名無しさん:2007/10/21(日) 09:46:09
プログラミングの知識がないままこれからC++を学ぶ人向けの本って
なかなかないような気がする。なんでだろうなぁ。

今なら一冊目が
やさしいC++ 第3版 http://www.amazon.co.jp/dp/4797343672/ になるのかな。
これだけじゃあ絶対無理だと思うから
二冊目として C++ Primer を読むことになるのかな。

個人的には
標準講座C++ http://www.amazon.co.jp/dp/4881357050/
章立てとかよく考えられててよかったなぁと思うけどもう絶版ぽくて
出版社のサイトでもリストから消えてた気がする。
413デフォルトの名無しさん:2007/10/21(日) 10:15:58
新・これならわかるC++―挫折しないプログラミング入門 (単行本)
小林 健一郎 (著)
http://www.amazon.co.jp/dp/4062129973

自分は読んだことないけど、こんなのはどうなんでしょう。
Accelerated C++、Effective C++を訳した人が自分で書いた本。
414デフォルトの名無しさん:2007/10/21(日) 10:57:16
詳説C++ 第2版
http://www.amazon.co.jp/dp/479732743X
店頭で立ち読みして検討した結果、これが一番よかった。
ほんとうはBjeane先生の本が一番好きなんだけど難しいからねえ。
415デフォルトの名無しさん:2007/10/21(日) 20:42:42
開発環境での相談なんですが...

研究者でデータ集めの道具として2年ほどC,C++を見よう見まねでいじっていました。
VS2005でなんとか自分のデータをいじるプログラムを作る事は出来ていたのですが、
サーバ側でデータをいじる必要がでて来て、LinuxでのC++統合開発環境を物色しています。

ずっと昔はemacs か mule ,少し前だとWideStudio, 最近はeclipse が定番のようですが、
アマチュア向けのC++開発環境としてVS2005から移行するのに今お勧めなのはどれ?
 
 
416デフォルトの名無しさん:2007/10/21(日) 20:45:47
eclipseでいいと思うよ
417デフォルトの名無しさん:2007/10/21(日) 21:03:08
メモ帳
418デフォルトの名無しさん:2007/10/21(日) 21:38:02
>>417
vi
419デフォルトの名無しさん:2007/10/21(日) 21:44:41
この辺が即答できないところがデスクトップとしてのLinuxの課題
420デフォルトの名無しさん:2007/10/21(日) 21:56:50
「サーバ側でデータをいじる必要」というのは単発的に必要なだけ?
それとも継続的に開発することになるのかな?
前者で、プラットフォームに依存したコードなんかもいらないなら、
開発は今までどおりVS2005でして、コンパイルだけLinuxですればいいと思う。
421デフォルトの名無しさん:2007/10/21(日) 22:22:09
>>415
eclipse以外に、KDEならKDevelopが、GNOMEならAnjutaが定番。
Windowsっぽさを求めるならKDEが無難。
422デフォルトの名無しさん:2007/10/22(月) 00:23:26
最近のGNOMEはAnjuta使われてないよ。
もっぱらEmacsで書かれてる。ついでにいうとほとんどPythonで。
423デフォルトの名無しさん:2007/10/22(月) 01:39:34
C++最大の注意点は1冊目何読むかだよな。
Cの場合K&Rでいいような気がするけどそれはどうよと突っ込まれる事もある。
424415:2007/10/22(月) 02:36:46
早速の御指導ありがとうございます。
>>420
継続的に必要になります。
今はデータを全部Windowsマシンにコピーしてそれを材料にしながらVS2005でコードを書いて
同じデストリのLinuxを入れたテスト系マシンに移してコマンドラインでコンパイルしなおして
さらに本番系にコピーしてしのいでいるのですが、どうも不自然な気がして....
も能率的なやり方とは思えないので.....
425デフォルトの名無しさん:2007/10/22(月) 10:57:25
>>424
WinScpを巧く使えば、ソースをLinux側に置いたままVSでコーディングと事前コンパイルだけすることができるよ。
# 勿論、一時的にWindowsに転送しているのは言うまでもないけど。

つーか、スレ違いなんでほどほどに。
426415:2007/10/22(月) 11:10:30
>>425
スミマセン、特定の環境のスレだと擁護者やらアンチやらがいて初心者にとっては
誰を信じて良いか判らなくなりそうだったのでここで聞きました。eclipseはJ系
の人が多そうなので、C++で使っている人の意見を聞きたかったんです。
427デフォルトの名無しさん:2007/10/22(月) 14:26:37
linux板の範疇だと思うがね。
428デフォルトの名無しさん:2007/10/23(火) 00:32:35
すいません教えてください。
boost の bind の練習で、rubyのeachのようなものを作ろうとしたんですが
エラーが下のように出てしまってうまくコンパイルできません。どこが問題なのでしょうか。

test1.cpp: In function `int main()':
test1.cpp:32: error: no matching function for call to `Foo::Foreach(boost::_bi::bind_t<void, void
(*)(int, int&), boost::_bi::list2<boost::_bi::value<int>, boost::arg<1> > >)'
test1.cpp:8: note: candidates are: void Foo::Foreach(T&) [with T = boost::_bi::bind_t<void, void (
*)(int, int&), boost::_bi::list2<boost::_bi::value<int>, boost::arg<1> > >]
429428:2007/10/23(火) 00:35:49
練習用のコードはこれです。
#include <iostream>
#include <boost/bind.hpp>
class Foo
{
 public:
  template <typename T> void Foreach( T& f)
  {
   for(int i= 0 ; i<10; ++i)
   {
    f(data[i]) ;
   }
  } ;
 private:
  int data[10] ;
} ;
void bar( int& data )
{
 data = 1234 ;
}
void hoge( int x, int& data )
{
 std::cout << data * x << std::endl ;
}
int main()
{
 Foo foo ;
 foo.Foreach( bar ) ;
 foo.Foreach( boost::bind( &hoge, 10, _1 ) ) ;
 return 0 ;
}
430デフォルトの名無しさん:2007/10/23(火) 00:36:13
エスパー出動!!
431デフォルトの名無しさん:2007/10/23(火) 00:39:41
>>429
ファンクタは値渡しで。
432デフォルトの名無しさん:2007/10/23(火) 00:43:17
>>429
またはconst T& なら通るんじゃない?

433429:2007/10/23(火) 00:54:03
>>431 >>432
ありがとうございます。
値渡し、const T&のどちらでもコンパイルがとおりました。
どうもありがとうございました。
434デフォルトの名無しさん:2007/10/24(水) 21:03:07
こういうこと思ったことない?

関数内でインスタンスごとのstatic変数(=関数内private変数)が欲しい!!



その関数内でしか使わないprivateな変数でもメンバ変数にしないとあかんやん

これって、ソースが膨大になった時ってこのprivate変数はどこでつかわれてるんやろうなって

探した結果、この関数内だけかい!!

って時に欲しくない?
435デフォルトの名無しさん:2007/10/24(水) 21:27:35
>>434
関数内 だったら 単なる Auto 変数 ってことじゃないの!?
436デフォルトの名無しさん:2007/10/24(水) 21:30:24
典型的なクラス分割のサインだと思う
437デフォルトの名無しさん:2007/10/24(水) 21:35:40
だな。
438デフォルトの名無しさん:2007/10/24(水) 21:42:48
>>434

class Foo
{
private:
int hoge;
public:
Bar(Foo f): { f.hoge = 99999; }
};

自分はこんなこと出来ちゃうのがちょっと気になる。
クラスごとでなく、インスタンスごとのprivate変数があれば、
こういう操作を禁止できるわけですよね?
439デフォルトの名無しさん:2007/10/24(水) 21:48:24
Bar(const Foo& f)
440デフォルトの名無しさん:2007/10/24(水) 22:02:46
あるクラス(test2)のオブジェクトを持つクラス(test)で、
testクラスのfriend関数からtestクラスにある
test2クラスのオブジェクトの参照をしようとすると
エラーになります。

class test2{
double d;
public:
test2(){d=10;}
double np(){return d;}
};

class test{
static test2 te;
public:
friend double xxx(double d){return te.np();}
};

これはだめですか?
441デフォルトの名無しさん:2007/10/24(水) 22:14:27
「友達の友達は友達だから、好き勝手にできる」と思って?
まずはその厚かましさを恥じろ。
test2はxxxを友達だなんて思って(宣言して)ないでしょ?
442440:2007/10/24(水) 22:24:12
返答ありがとう。

>>440のコードそのまま貼り付けたままならビルドできましたが
void main(){
cout<<xxx();
}

のように使うと駄目みたいです。

えーと、本当にやりたいことは
クラスのメンバ関数を関数ポインタに入れられないかと思いまして、
だからと言って、そのままやるとできなかったので、
一旦friend関数か何かを経由してやればできるかなぁと考えました。
無理みたいでしたけど。

(C言語でかかれたコードで、関数ポインタを渡して使う関数があったので、
 どうにかしてC++で作ったクラスのメンバ関数を渡せないかと考えてます)
443デフォルトの名無しさん:2007/10/24(水) 22:53:21
どうダメなんだ?

friend double xxx(double d){return te.np();}
を呼ぶつもりなら

void main(){
cout<<xxx();
}
は xxx に引数がないようだが?
444デフォルトの名無しさん:2007/10/24(水) 22:53:32
>>435
Auto変数じゃなくてstatic。関数を抜けた後も値を保持してるってこと
445デフォルトの名無しさん:2007/10/24(水) 22:58:11
>>436
ってことは、C言語の時は関数内でstatic変数を使用したことがないってことですか?
446デフォルトの名無しさん:2007/10/24(水) 22:59:43
>>436
もし、そうでしたらC言語の場合はモジュール分割ってことになるんですよね?
447デフォルトの名無しさん:2007/10/24(水) 23:01:32
>>442
静的メンバ関数なら普通の関数へのポインタへ変換できる。
こっちから関数への引数を1つくらい
渡せれば、(例えばWinAPIのEnumWindowsのように)
それを使って非静的関数も呼べる。
448デフォルトの名無しさん:2007/10/24(水) 23:03:36
>>438
こういうのは不思議に思ったことがあるんだけど
そういうことではないんだよね
449デフォルトの名無しさん:2007/10/24(水) 23:23:03
メンバ関数の先頭でthisポインタと比較すればいいんじゃね
実行時のアクセス制御になっちゃうけど
450440:2007/10/24(水) 23:26:25
>>443
あ、すいません
void main(){
cout<<xxx(0.0);
}
でも駄目です。

error C3767: 'xxx': 候補の関数はアクセス可能ではありません。
1> '.\NNN.cpp(30)' の friend 関数である可能性があります : 'xxx' [引数依存の照合を使って検出される可能性があります]

こんなエラー文になります
451440:2007/10/24(水) 23:36:07
>>442
こんなふうにしても駄目でした。

class test;
class test2{
friend test;
double d;
public:
test2(){d=10;}
double np(){return d;}
};

class test{
static test2 te;
public:
static double x;
static double xxx(double d){return x;}
};

void main(){
cout<<test::xxx(0.0)<<endl;
}

変なエラーが出ます。
452デフォルトの名無しさん:2007/10/24(水) 23:37:00
>>445
メンバ変数と関数内static変数ではライフサイクルが違うじゃないか
>>434の話と違っている
453440:2007/10/24(水) 23:51:32
アッー!!
変数の再宣言忘れてました・・・
どうも、おつかれさまです
454デフォルトの名無しさん:2007/10/24(水) 23:55:48
>>452
そう?

クラス分割のサインって言うのはちょっといいすぎな気が・・・。
もちろん、時と場合によるけど。

ただ、privateなインスタンス変数より、さらにアクセスが厳しくなるんですよ!!

privateなインスタンス変数だとクラス内から使用できるけど、関数内インスタンス変数はその関数内でしか使えない。

よくないかい?
455デフォルトの名無しさん:2007/10/24(水) 23:58:54
>>452
C言語でもC++みたいな、すなわちクラスみたいに作成したら結局同じかなっと思ってるんですけど・・・。

私は、C言語でもクラスみたいに書いてたので・・・。
456デフォルトの名無しさん:2007/10/25(木) 00:08:24
>>453
関数ポインタでやるんだったら、関数ポインタでやらないと。
フレンドなんか滅多に使うことはないんだから。

関数ポインタがあるってことは、イベントを呼ぶってことでしょ?

そのソースの目的を見失わないようにね
457デフォルトの名無しさん:2007/10/25(木) 00:27:34
メンバ関数内staticな変数(クラスメンバではない)を使いたいってことだよね
うーん……
458デフォルトの名無しさん:2007/10/25(木) 00:54:27
その関数と変数をクラス化して集約させるのが普通だと思うが。
関数が2個以上の場合でも汎用的に使えるし。
459デフォルトの名無しさん:2007/10/25(木) 01:43:56
class Foo{
int v;
public:
Foo(int a = 10):v(a){}
int get(){return v;}
};
class Bar{
static Foo f1;
Foo f2;
public:
friend int func1();
friend int func2(Bar);
};
Foo Bar::f1;
int func1(){return Bar::f1.get();}
int func2(Bar b){return b.f2.get();}
int main ()
{
std::cout << func1();
Bar b;
std::cout << func2(b);
return 0;
}
460デフォルトの名無しさん:2007/10/25(木) 02:07:49
クラス内でのfriend関数の宣言、定義はprivateなメンバへの参照とは関係ない。
(Effective C++ 第3版の24項と46項を参照)
461デフォルトの名無しさん:2007/10/25(木) 02:14:59
>>460
friend によって非メンバ関数になる
第一引数はそのクラスのオブジェクトでないと駄目
462デフォルトの名無しさん:2007/10/25(木) 02:52:06
stl の begin, end などは引数が void の関数オーバーロードなのにどうして戻り値が const_iterator か iterator かを判別できるんですか?
使用先で関数を推論しているのかと思い同じような事をしてみたんですが、どうにもうま最適なく関数を絞り込めないようです。
463デフォルトの名無しさん:2007/10/25(木) 02:55:43
ue
464デフォルトの名無しさん:2007/10/25(木) 03:24:20
>>462
iterator vector::begin();
const_iterator vector::begin() const;

↑これが↓こんな感じでオーバーロード解決される。

iterator vector_begin(vector* this);
const_iterator vector_begin(vector const* this);
465デフォルトの名無しさん:2007/10/25(木) 03:32:49
奈良自分で同じような事する場合はどうすりゃいいの
466デフォルトの名無しさん:2007/10/25(木) 05:39:48
同じことをすれば、勝手にやってくれるだろう。
そうなってくれないとしたら、それは何らかの意味で「違うこと」をやっているのでは。
467デフォルトの名無しさん:2007/10/25(木) 07:57:10
stlのソース読めば?
468デフォルトの名無しさん:2007/10/25(木) 10:12:04
>>457
ごめん。言い方が少し悪かったです。反省します。

staticという言葉は無視してください

まとめると
「関数内でしか使えないメンバ(インスタンス)変数が欲しい」ってことです
なのでもちろんクラスのメンバです。
469デフォルトの名無しさん:2007/10/25(木) 11:33:13
32bit表現の浮動小数点数を10進数に直せるプログラムってあるんですか?
いくらぐぐってもみちかんない……
470デフォルトの名無しさん:2007/10/25(木) 11:35:46
>>469
std::istringstream
471デフォルトの名無しさん:2007/10/25(木) 11:41:11
こんな感じだな

#include <iostream>
#include <sstream>
#include <iomanip>

int main()
{
float f = 3.14f;

std::ostringstream s;
s << std::setprecision(4) << std::showpoint << f;
std::cout << s.str() << std::endl;
}
472デフォルトの名無しさん:2007/10/25(木) 12:04:34
>>469
32bit表現の浮動小数点数とは IEEE-754 のことですか?
そういうのは標準関数ではないと思います。
473デフォルトの名無しさん:2007/10/25(木) 13:32:01
出来ない……標準関数じゃないのか……
そもそもC++にこだわる必要ないんだった……
他スレ行ってきます。
474デフォルトの名無しさん:2007/10/25(木) 18:27:05
std::stringstream ss;
float x = 12.34;
ss << x;

でいいんじゃないの?
475474:2007/10/25(木) 18:27:44
ウボァ
476デフォルトの名無しさん:2007/10/25(木) 19:01:54
int** a = new int*[2];
a[0] = new int[3];
a[1] = new int[2];
for(int i=0; i<3; ++i) a[0][i] = i;
for(int i=0; i<2; ++i) a[1][i] = i;

とかやったときに、a[0]行の配列のサイズを知る方法ってありますか?
sizeof()を使ってもうまく出力できません。
477デフォルトの名無しさん:2007/10/25(木) 19:22:02
素直にvectorでも使ってろ
478aho:2007/10/26(金) 00:16:40
動的にメモり確保してるんだから、単純に
int a0_size = 3;
int a1_size = 2;
int ** a = new int*[2];
a[0] = new int[a0_size];
a[1] = new int[a1_size];
.......
printf("size of a0 is %d\n", a0_size);

では、あかんのかね?
これでも十分なきがするけど・・・
479デフォルトの名無しさん:2007/10/26(金) 18:38:39
こんなコード保守する羽目になったらformat c: だな…('A`)
480デフォルトの名無しさん:2007/10/26(金) 22:03:30
リストを関数に渡したり、クラスの外部にリストを公開する場合って
どんな方法使ってる?

begin()とend()?
481デフォルトの名無しさん:2007/10/26(金) 23:56:41
以下の様な形でstaticなメンバをcppで宣言する際に
/* a.h */
class a{
 static type_0 m0;
 static type_1 m1;
};

/* a.cpp */
type_0 a::m0(123);
type_1 a::m1(a::m0);//m1はコンストラクタでtype_0の変数を必要とする

プログラムの都合上a::m0はa::m1の前に初期化されている必要があるんですが、
m0がm1の前に初期化されているという保証はあるんでしょうか?
482デフォルトの名無しさん:2007/10/26(金) 23:57:11
宣言じゃなくて、定義か。
483デフォルトの名無しさん:2007/10/26(金) 23:57:17
プログラムを実行した後、
Dos画面がすぐに閉じてしまうのですが
「何かキーを押してください」のような画面を表示して待機するためには
どうするのが普通なのでしょうか
484デフォルトの名無しさん:2007/10/26(金) 23:58:41
>>483
VS2005ならCtrl + F5でデバッガに乗せずに実行
デバッガに乗せて実行するなら、<conio.h> _getch()を実行
485デフォルトの名無しさん:2007/10/27(土) 01:04:35
>481
同一翻訳単位であれば定義した順序に初期化される(3.6.2/1)。
ただし、翻訳単位が異なる場合は順序が不定であり、static initialization order fiasco として知られる問題を引き起こす。
ttp://www.parashift.com/c++-faq-lite/ctors.html
の、10.12 以降を参照。
486デフォルトの名無しさん:2007/10/27(土) 01:28:55
ビルドした.exeをダブルクリックで実行したときの
フォルダの情報と、
ファイルをドラッグ&ドロップしたときのフォルダの情報が
違うのですが、
どうやって対処したらよいですか
487デフォルトの名無しさん:2007/10/27(土) 01:33:05
多分Windowsのことだと思うがカレントディレクトリについて勉強する。
そしてそういうのはスレ違いだから二度と質問しないように。
488デフォルトの名無しさん:2007/10/27(土) 01:33:22
俺のエスパー能力が、>>486の意味するところはカレントディレクトリだと告げているが、
俺には力不足だ。
489デフォルトの名無しさん:2007/10/27(土) 01:34:22
>>487-488
ケコ━━━━(・∀・)人(・∀・)━━━━ン
490486:2007/10/27(土) 01:49:51
そうなんですか?
ドラッグ&ドロップした場合は2番目の引数の文字列に
c:\xxxx\file.txt
ってなるので
c:\xxxx\
の部分だけ抽出して対処しようとしたのですが
もっと普通の方法があると思って質問しました。まあいいや。

c:\xxxx\
を抽出して、そのあとに任意のファイル名の文字列を追加する
いい方法あるでしょうか。
491デフォルトの名無しさん:2007/10/27(土) 01:53:26
だめだ、俺のエスパー能力をはるかに超えた強敵だった。
とりあえず言えることは、ファイルパスを分離する標準ライブラリはない。
492デフォルトの名無しさん:2007/10/27(土) 02:08:02
_splitpath
493デフォルトの名無しさん:2007/10/27(土) 02:09:48
どういう育ち方をすると、ここまで説明が下手になるんだろうな。
それとも、「自分の頭の中にあるものは、そのままでは相手には見えない」ということに
まだちゃんと納得できていない年齢なのか?
494デフォルトの名無しさん:2007/10/27(土) 02:28:46
自分が何を分かっていないかを的確に説明できる奴は、そもそもこういうとこで質問するまでもなく自分で解決できちゃうからだよ
495デフォルトの名無しさん:2007/10/27(土) 02:38:05
そうじゃない
できてないのは起こった問題の説明
496デフォルトの名無しさん:2007/10/27(土) 04:03:09
vector<int,vector<int>> v;
みたいなことできなかったけ?
497デフォルトの名無しさん:2007/10/27(土) 04:10:24
>>496
vector<vector<int> > v;
ならできるが。
498デフォルトの名無しさん:2007/10/27(土) 04:14:55
using namespace std;

class A{
int x;
vector<int> y;};

vector<int> z;
499デフォルトの名無しさん:2007/10/27(土) 04:17:23
class A{
int x;
vector<int> y;};

vector<A> z;
500デフォルトの名無しさん:2007/10/27(土) 04:17:45
int → A?
501デフォルトの名無しさん:2007/10/27(土) 04:19:34
>>500
22秒差・・・
502デフォルトの名無しさん:2007/10/27(土) 04:34:59
vector<pair<int, vector<int> > > v;
だな。やるなら。
503デフォルトの名無しさん:2007/10/27(土) 04:37:48
vectorの中にいろいろ入れるとわかりづらい classでまとめよう
504デフォルトの名無しさん:2007/10/27(土) 04:43:29
typedefじゃない? いちいち class 使う?
505デフォルトの名無しさん:2007/10/27(土) 12:17:57
用途が不明だから外れているかもしれないけど、
map<int, vector<int> >とかmultimap<int, vector<int> >はどう?
506デフォルトの名無しさん:2007/10/27(土) 12:29:33
typedef pair<int, pair<int, pair<int, pair<int, vector<pair<int, pair<int, pair<int, vector<int> > > > > > > > > type;
507デフォルトの名無しさん:2007/10/27(土) 12:31:44
pair<
 int,
 pair<
  int,
  pair<
   int,
   pair<
    int,
    vector<
     pair<
      int,
      pair<
       int,
       pair<
        int,
        vector<
         int
        >
       >
      >
     >
    >
   >
  >
 >
>
508486:2007/10/27(土) 12:52:16
なんか色々言われてるけど
できたからいいよ。

とりあえず役立たずの>>493は死んでいいよ
509デフォルトの名無しさん:2007/10/27(土) 12:59:05
>>508
たしかに>>493は口が悪いから怒るのも分かるが、>>508の最後の1文も醜い。
やってることは同レベルだ。
つまらない仕返しなどせず、ほっとけ。

それと説明が下手だというのは事実だから、素直に受け止めたほうがいい。

そして俺もスレ汚し。すまそ。
510デフォルトの名無しさん:2007/10/27(土) 13:37:30
>>505-507
なんというリスト構造…
511デフォルトの名無しさん:2007/10/27(土) 15:22:47
コンパイルエラーのときに出る、
”実体化”
というのがわからないんですが、
これは何ですか?
512デフォルトの名無しさん:2007/10/27(土) 15:23:32
テンプレートのインスタンス化
513デフォルトの名無しさん:2007/10/27(土) 20:14:29
>>509
ある程度の年齢に達したお馬鹿さんというのは
「指摘を活かせない人生を送ってきたから今そうしてそこにいる」わけで、
そういう人に指摘しても無駄。イジることに終始してたほうが面白いよw
514デフォルトの名無しさん:2007/10/27(土) 20:22:25
でも2chにしろネットにしろ、自分の身分を隠せるから普段恥ずかしくて人に訊けない様な事はどんどん聞けて便利だよねフヒヒh
515デフォルトの名無しさん:2007/10/27(土) 20:23:50
同感ふふぃふぃふぃ
516デフォルトの名無しさん:2007/10/27(土) 20:25:51
あんまりマニアックな事になると誰も答えてくれないけどね…
cppllは閑古鳥無いてるし
どこか良いコミュニティはないものか
517デフォルトの名無しさん:2007/10/27(土) 20:28:36
ここでマニアックな質問が放置されたことなんて最近あったか?
スレ違いならずっとあるけど。
518デフォルトの名無しさん:2007/10/27(土) 20:30:41
みんなcppよりも大事な事があるんだよ
519デフォルトの名無しさん:2007/10/27(土) 20:44:07
>>518
hppだよな
520デフォルトの名無しさん:2007/10/27(土) 23:04:56
adobeのdng_sdkのコードを読んでるんだけど、メンバ変数名の頭に f がくっついています。
これって何の略なんでしょか。friendではなさそうだし、fuckもあえりない。
気になってしゃあないっす。。。
521デフォルトの名無しさん:2007/10/27(土) 23:07:19
field の略じゃねーの?
522デフォルトの名無しさん:2007/10/27(土) 23:10:59
203 名前:198 [sage]: 2007/10/26(金) 03:26:09
Exceptional C++ Style
P.29
>・デフォルトパラメータを持つメンバー関数のシグニチャは、
> 「等価な振る舞いを持つ2つ以上のメンバー関数のシグニチャ」に
> 置き換えても良い。
>・メンバー関数のシグニチャには、追加のデフォルトパラメータが
> 含まれていても良い。
P.30
>つまり、コードの移植姓を保ちながら標準ライブラリのメンバー関数
>へのポインタを生成することは不可能なのだ。


理解できん。ここで教えてくれw
523デフォルトの名無しさん:2007/10/27(土) 23:11:53
Exceptional C++ Style嫁
524デフォルトの名無しさん:2007/10/28(日) 00:21:38
>>522
Exceptiol C++ Style は持ってないおれが説明してやるからちょっと待ってろ。

まず、そのルールは規格の 17.4.4.4 にある記述に対応するもの。言い回しや
順番は違うけど同じことを言っている。
525デフォルトの名無しさん:2007/10/28(日) 00:21:59
見た目上のシグネチャが標準準拠ならデフォルト引数を使っていいよ
【実装者A】
うはwwwww
list.clear(int hogehoge = 8)
【実装者B】
おkwwwww
list.clear(bool hige = false)
【使う人】
ちょwww関数ポインタに移植性ナスwwwwwwww
526524:2007/10/28(日) 00:22:10
>>522 (1/2)
長くなったからレス2つに分けるよ。

以下のクラス S とそのメンバ関数 foo が標準関数として規定されている場合。
  // 規格の表記
  struct S {
      int foo(int a, int b = 0);
  };
以下の実装はどちらも >522 に挙げられた明示的な許可によって、規格に
準拠したものと言える。
  // 実装 A
  struct S {
      int foo(int a) { return foo(a, 0); }
      int foo(int a, int b);
  };
  // 実装 B
  struct S {
      int foo(int a, int b = 0, c = 1);
  };
527524:2007/10/28(日) 00:22:42
>>522 (2/2)

規格の表記にある S::foo(int, int) へのポインタを使って、以下のような
コードを書くことが考えられる。
  void f(std::vector<int>& v, S& s, int x) {
    std::for_each(v.begin(), v.end(), boost::bind(&S::foo, s, x, _1));
  }
実装が規格のとおりであればこのコードは問題なくコンパイルでき、意図した
とおりに動作する。

しかし実装 A のように実装されていた場合、 &S::foo では
オーバーロードされた2つの S::foo うちのどちらかコンパイラは判別
できず、コンパイルエラーになる。その場合、コードを以下のように
変更することで問題を回避できる。
  void f(std::vector<int>& v, S& s, int x) {
    std::for_each(v.begin(), v.end(),
      boost::bind(static_cast<int (S::*)(int, int)>(&S::foo), s, x, _1));
  }
このコードは規格の表記のとおりの実装と、実装 A の両方に対応できて
いる。

しかし実装 B のように実装されていた場合、 int (S::*)(int, int) に
マッチする S::foo は存在しないので、コンパイルエラーとなってしまう。

現状の規格ではどの実装も規格に準拠したものとされてしまうため、すべてに
対応するような(移植性のある)方法で S::foo へのポインタを使うことは
できない。
528デフォルトの名無しさん:2007/10/28(日) 01:09:33
質問なんですが、Typelistを使わないでテンプレート引数の数を可変にすることはできますか?
下のようなScatteredHierarchyクラスを習作で作ってみたんですが、なんとかTypelistを見せないようにしたいんです。

・テンプレート引数にTypelistが必要なScatteredHierarchy
template <class T> struct ScatteredHierarchy ;
template <class T, class U> struct ScatteredHier: public T, public ScatteredHierarchy<U>{} ;
template <> struct ScatteredHierarchy<NullType> {} ;
529528:2007/10/28(日) 01:12:08
× template <class T, class U> struct ScatteredHierarchy : public T, public ScatteredHierarchy<U>{} ;
○ template <class T, class U> struct ScatteredHierarchy<Typelist<T,U> >
: public T, public ScatteredHierarchy<U>{} ;
530デフォルトの名無しさん:2007/10/28(日) 01:21:56
任意個は無理だが個数限定ならデフォルト引数でいけるんじゃないかな
531デフォルトの名無しさん:2007/10/28(日) 01:24:47
>528
C++0xにならないとムリみたい。
とりあえずはboost::mplで我慢
532528:2007/10/28(日) 10:29:13
>>530 >>531
ありがとうございます。
デフォルト引数とmplの両方を使ってみてもう少し考えてみます。
533デフォルトの名無しさん:2007/10/28(日) 10:39:55
可変個テンプレート引数といえばむしろBoost.Preprocessor
534デフォルトの名無しさん:2007/10/28(日) 13:42:41
IDirectDrawSurface7 * DXC_ddraw::pCreateOffScreenSurface( DWORD dx, DWORD dy )
{
  IDirectDrawSurface7 * pdds;

 // 色々

 retrun pdds;
}
上記のようなソースを見たのですが、このメンバ関数を2回以上呼び出すと
最初の同じppdsの値を何回も返したりしないのでしょうか?
535534:2007/10/28(日) 13:47:24
すんません、自己解決しました。
色々のところで初期化(CreateSurface)してました。
536デフォルトの名無しさん:2007/10/28(日) 13:48:23
最初も何も、pddsを宣言した時点では初期化していないのでpddsの値は不定。
「//色々」のところを省略されては、答えようがない。
537デフォルトの名無しさん:2007/10/28(日) 13:52:48
>>536
なるほどpddsの値は不定ですか
勉強なりますた
538デフォルトの名無しさん:2007/10/28(日) 14:36:17
>>527
ありがとう。やっと理解できた。ありがとー
539デフォルトの名無しさん:2007/10/28(日) 14:44:29
template < class T, class T1 > struct s< T (*)(T1) >{ typedef T result; };
template < class T, class T1 > f( T (*p)(T1) ){
 typename s<T (*)(T1)>::result r;
}
int F(char){...};
void test(){
typename s< &F >::result r; //エラー
f( &F ); //エラーじゃない
}

こうなるのは何でですか?
540デフォルトの名無しさん:2007/10/28(日) 15:04:35
>>539
まず、まともにコンパイルできるものをだせよ。
クラスsのプライマリテンプレートがないし、
関数fに戻り値がない。
関数testはテンプレートではないので、中でtypenameは使えない。

あと、何が疑問なのか分からん。
クラスsのテンプレートパラメータに渡せるのは型だ。

&F ; //これは関数Fへのポインタ、int(*)(char)型への値
int (*)(char) ; // これは関数Fへのポインタの型
541デフォルトの名無しさん:2007/10/28(日) 17:08:33
template<class T> struct foo{};
int main(){ foo<int>::foo a; }

でこれのコンパイルが通ってしまうんですが、理由がわかりません。
::foo のところです。

どなたか教えてください。
542541:2007/10/28(日) 17:14:30
struct bar{};
int main() {
  bar b1;
  bar::bar b2;
  bar::bar::bar b3;
}

これも通るんですね。。
何故?!
543デフォルトの名無しさん:2007/10/28(日) 17:28:49
>>541-542
クラス名自身がクラスのメンバとして登録されているから。
メンバになってるクラス名は "injected-class-name" と呼ばれる。

規格の 9 (Classes) p2 より
> A class-name is inserted into the scope in which it is declared immediately after the class-name is seen.
> The class-name is also inserted into the scope of the class itself; this is known as the injected-class-name.
> For purposes of access checking, the injected-class-name is treated as if it were a public member name.
544デフォルトの名無しさん:2007/10/28(日) 17:32:35
>>543
ありがとうございます!
545デフォルトの名無しさん:2007/10/28(日) 17:38:00
visual C++ 2005では通らない…
gccの方が準拠度はいいのか?
546デフォルトの名無しさん:2007/10/28(日) 17:45:25
>>545
へえ。VC++はもってないのだが、

typedef struct bar_ {
  typedef struct bar_ bar;
} bar;

とか,

struct bar_ {
  typedef struct bar_ bar;
};
typedef struct bar_ bar;

とかすれば同じ事ができる?
547デフォルトの名無しさん:2007/10/28(日) 18:15:12
できてもうれしくない。

そもそも何のために規格でこんなことを決めているのかわからない。
548デフォルトの名無しさん:2007/10/28(日) 18:27:06
こんな感じなのかな。

class Base
{
protected :
  int value ;
} ;

class Derived : public Base
{
  int value
  void f()
  {
    value = 0 ; //どっちのvalueなのかややこしい
    Base::value = 0 ;
    Derived::value = 0 ;
  }
} ;
549デフォルトの名無しさん:2007/10/28(日) 18:28:56
は?
550デフォルトの名無しさん:2007/10/28(日) 18:38:58
>>547
クラス(構造体)名に限って、同じスコープにある他の型と名前が重複しても
ODR違反にならないため、
  int f;
  struct f { int i; };
と書ける。このとき、単にfと書くとint型の方が、f::fと書くとstructの方が選ばれる。
  int main() {
    f a;  // [ERROR] int型のfが選ばれるが、「<識別子> <識別子>」という構文はない
    f::f b; // [OK] struct fの方が選ばれる
    f = 1; // [OK] int型のfに1を代入
    return 0;
  }
551デフォルトの名無しさん:2007/10/28(日) 19:00:03
>> 541
gccのバグ
規格の3.4.3.1/1a 見ろ。
552デフォルトの名無しさん:2007/10/28(日) 19:04:40
>>550
その場合は struct f と書けばいい。 f::f が必要な理由にはならない。
553デフォルトの名無しさん:2007/10/28(日) 19:06:05
>>551
規格的に、>>541はNGで>>542はOKということ?
554デフォルトの名無しさん:2007/10/28(日) 19:07:00
>>551
すまんがいま手元に本がない。簡単に何が書いてあるか教えて。
555デフォルトの名無しさん:2007/10/28(日) 19:10:24
3.4.3.1 (Class members) p1a より
> If the nested-name-specifier nominates a class C, and the name specified after the nested-name-specifier,
> when looked up in C, is the injected-class-name of C (clause 9), the name is instead considered to name the
> constructor of class C. Such a constructor name shall be used only in the declarator-id of a constructor definition
> that appears outside of the class definition.
556デフォルトの名無しさん:2007/10/28(日) 19:13:18
>>553 どっちも駄目。
557デフォルトの名無しさん:2007/10/28(日) 19:14:51
>>551,555
だがしかし。
http://www.open-std.org/jtc1/sc22/wg21/docs/cwg_defects.html#318

gcc はこいつを先取りしてる、とか?
558デフォルトの名無しさん:2007/10/28(日) 19:17:52
おまいら・・・何食ったらそんな詳しくなれるんだ。
559デフォルトの名無しさん:2007/10/28(日) 19:22:43
暗記パン
560デフォルトの名無しさん:2007/10/28(日) 19:35:34
n2315 見たら >557 の DR 318 が取り込まれてるっぽいんだが、
A::A はやっぱり駄目で struct A::A は OK とか、もうさっぱり意味がわからない。

> A::A a; // error, A::A is not a type name
> struct A::A a2; // object of type A
561デフォルトの名無しさん:2007/10/28(日) 20:54:00
2315って古くない?
562デフォルトの名無しさん:2007/10/28(日) 21:34:06
n2369 が出てた。この話題に関係あるところは同じだったけど。
563デフォルトの名無しさん:2007/10/29(月) 23:04:27
質問なんですがあるクラスの親クラスの型をコンパイル時に取得する方法ってありますか?
親クラスの型毎にクラステンプレートの特殊化を定義したいのですが方法がわからないのです
564デフォルトの名無しさん:2007/10/29(月) 23:06:27
>>563
無いはず。あるとしたら、多重継承したときにどうなるのかわからない。
565デフォルトの名無しさん:2007/10/29(月) 23:13:35
>>563
boost::is_base_ofでenable_ifとかそういう話じゃなくて?
566563:2007/10/29(月) 23:53:59
>>564 >>565

レスありがとうございます。
is_base_ofの使い方を調べてみます。
567デフォルトの名無しさん:2007/10/30(火) 00:17:16
>>566
調べてみるのはいいが、せめてこれ ttp://www006.upp.so-net.ne.jp/yotto-k/doc/tmp.pdf の60ページ前後まで理解できないとつらいとおもうよ。
568デフォルトの名無しさん:2007/10/30(火) 00:31:59
下のような擬似2次元配列クラスを作っていて、
現在GetValueをオーバーロードすることで
1次元的にも2次元的にもアクセスできるようにしています。
それに加えて添字演算子を使って
[i]で1次元的、[x][y]で2次元的にアクセスできるようにしたいのですが
何かよい方法はないでしょうか?
1次元、2次元どちらかだけ対応させることはできるのですが
両方に対応させる方法が思いつきません。
template<class T> class CArray{
T* m_array;
int m_width;
int m_height;
public:
//中略
//1次元的アクセス
T& GetValue( int i ) {
return m_array[i]; }
//2次元的アクセス
T& GetValue( int x, y ){
return m_array[ y*width + x ]; }
};
569デフォルトの名無しさん:2007/10/30(火) 00:33:11
つ[proxyクラス]
570デフォルトの名無しさん:2007/10/30(火) 00:34:59
つ more effective C++
571デフォルトの名無しさん:2007/10/30(火) 01:10:00
>>570 と more effective C++ を持ってる香具師
その本買う価値ある?
572デフォルトの名無しさん:2007/10/30(火) 01:15:17
翻訳がこれ以上はないというほどひどいけど、代理クラスについて
簡単に知ろうと思うなら買っとけ。
573デフォルトの名無しさん:2007/10/30(火) 03:29:21
ちょっと混乱してよく分からない状態なのですが
T** ptr; のとき
ptrをdeleteするとptrが保持してたポインタも一緒にdeleteされてしまいますか?
574デフォルトの名無しさん:2007/10/30(火) 03:37:07
int *p; のとき
pをdeleteすると、pの示す先(*p)に0が代入されると思いますか?
575デフォルトの名無しさん:2007/10/30(火) 03:37:37
されるわけがない。
576デフォルトの名無しさん:2007/10/30(火) 04:54:17
>>568とほぼ同じことをするためにproxyクラスを使う必要があって
more effective c++を買った。
該当部分の翻訳:
> そのようなクライアントは、あたかもアラーの神に忠実な本物の生々した2次元配列を使ってプログラムする。
は、いまだに何を言ってるのかサッパリだが、ソースコード部分は(他の節も含め)とても参考になった。
吉川さんが訳してくれればいいのに……。
577デフォルトの名無しさん:2007/10/30(火) 06:54:21
すげえな。原書では
>Such clients program as if they were using real, live, honest-to-Allah two-dimensional arrays.
になってる。honest-to-Allah は「神に誓って」ぐらいで強調でしかないだろうから、
「そのようなクライアントは、まるで本当に本物の2次元配列を使っているかのようにプログラムを書くことになる」
くらいでいいんじゃないかと思う。
578デフォルトの名無しさん:2007/10/30(火) 07:24:15
そんな原文だったのか。卒研生の輪講並に酷い訳文だなぁ。
うーん、やはり原書を買った方がいいな……英語のがはるかにわかりやすい。
>>577ありがとう。やっと決心がついた。
579デフォルトの名無しさん:2007/10/30(火) 13:08:18
////classA.h////
#ifndef CLASSA_H_
#define CLASSA_H_
template<class T> class A {
publilc:
void func(T);
};
#endif

////classA.cpp////
#include "classA.h"
template<class T> void A<T>::func(T t) {
//略
}

////test.cpp////
#include "classA.h"
int main() {
A a;
a.func(T); // Tについては略
// 以下略

このときmain内でfuncなんてねーよって怒られるのですが
どう解決したらいいのかわかりません
どなたかご教授を・・・
580デフォルトの名無しさん:2007/10/30(火) 13:23:20
テンプレートの内容は全部ヘッダに書いておく
581579:2007/10/30(火) 13:34:14
具体的にどのように書いたらいいのでしょうか
582デフォルトの名無しさん:2007/10/30(火) 14:28:25
>>581
>>579

////classA.h////
#ifndef CLASSA_H_
#define CLASSA_H_
template<class T> class A {
publilc:
void func(T);
};
- #endif

- ////classA.cpp////
- #include "classA.h"
template<class T> void A<T>::func(T t) {
//略
}
+ #endif

////test.cpp////
#include "classA.h"
int main() {
- A a;
- a.func(T); // Tについては略
// 以下略
583デフォルトの名無しさん:2007/10/30(火) 14:35:11
>>581
////classA.h////
#ifndef CLASSA_H_
#define CLASSA_H_
template<class T> class A {
publilc:
void func(T t) {
//略
}
};
#endif
584579:2007/10/30(火) 14:45:14
>>582-583
そいういうことだったんですね
なんとなくtemplateについて解ってきた気がします
ありがとうございました
585デフォルトの名無しさん:2007/10/30(火) 19:28:25
templateって多用するとバイナリ大きくなるから
組み込みではほとんど使われないと聞いたが
メモリの使用量も同様に増えるもん?
何だかスレ違いですまん
586デフォルトの名無しさん:2007/10/30(火) 19:45:12
>>585
そんなことない。
587デフォルトの名無しさん:2007/10/30(火) 21:15:36
>>585
実行バイナリのテキスト部分、つまりマシン語のコードの分もメモリ食うから、その分は消費が増えていると言える。
ヒープやスタックを余分に食うかはコードの書き方によるが、ヒープの消費は若干減るケースが多いと俺は思う。
588デフォルトの名無しさん:2007/10/30(火) 21:38:53
>>585
仕組みを考えれば分かるだろ
589587:2007/10/30(火) 21:45:22
おっと組込みか。組込だと、バイナリの分はRAMは喰わないこともあるな。ま、自分で考えてw
590デフォルトの名無しさん:2007/10/30(火) 21:56:31
591デフォルトの名無しさん:2007/10/30(火) 22:01:37
>>576-577
初版や原書持ってないから場所間違ってるかもしれないけど、2版の場合こうなってる。
「そのようなクライアントは、実在する、生きた、本当の2次元配列を使っているかのようにプログラムする」

まあ、割と普通。初版は相当キてるようだね
592デフォルトの名無しさん:2007/10/30(火) 23:00:57
英語の小説とかだとあらすじがうっすら解るぐらいなのに
技術書は英語でもスラスラ読めるよね
不思議なもんだ
新聞も読めない
593デフォルトの名無しさん:2007/10/30(火) 23:04:21
>>591
十分意味不明な気がするぞ…w
594デフォルトの名無しさん:2007/10/30(火) 23:05:55
実在する、生きた

とかいらねぇぇぇ
595デフォルトの名無しさん:2007/10/30(火) 23:11:53
 >そのようなクライアントは、「そのようなクライアントは、実在する、生きた、本当の2次元配列を使っているかのようにプログラムする」2次元配列を使っているかのようにプログラムする
これのどこが普通なんだ?
まずクライアントってのが変だろ。どう考えても。
ここは思い切って、「ライブラリを使用する側にとっては」などにしておいたほうが分かりやすいだろう。
「実在する、生きた、本当の」ってのも、くどすぎるだろ。アラーに忠誠を誓うのとあまり代わり映えしてないぞ。
「あたかも、本当に2次元配列であるかのように」などのように、何で出来なかったのか。
あと、「プログラムする」って何か違和感がある。
「プログラミングする」、とか、「コーディングする」という言い回しならそういう違和感も感じないんだが。

ハリポタや戸田奈津子並だな。
596デフォルトの名無しさん:2007/10/30(火) 23:21:28
クライアントは普通だと思う
この業界ではよく使うし
597デフォルトの名無しさん:2007/10/30(火) 23:23:28
原文でもくどく書いてる
598デフォルトの名無しさん:2007/10/31(水) 08:57:44
char (&test(...))[3]
ってどういう意味ですか?
599デフォルトの名無しさん:2007/10/31(水) 09:44:20
このシリーズで使われている「クライアント」という用語の意味については
ちゃんと書いてあるのに。業界とか何の関係も無いし。

EffectiveC++すら読んでないということだね。
600デフォルトの名無しさん:2007/10/31(水) 09:49:14
現在注目しているコードを使用する側のコードの事だっけ
デザパタ系の解説記事とかでよく見る気がする
601デフォルトの名無しさん:2007/10/31(水) 09:49:27
一応書いておくと、
筆者は、STLのような「再利用可能な実用的なライブラリ」を書く、という立場で記述している。

つまり、この本での「クライアント」とは、「ライブラリの利用者」のこと(ちゃんとそう書いてある)。
それを前提を知っている人から見れば、>>591はそんなにおかしくはない。
602デフォルトの名無しさん:2007/10/31(水) 10:26:05
>>595
書籍や映画の字幕と較べるのは如何なものかと。
# それに、あの脱税社長と較べたら戸田さんが可愛そうだ。
603デフォルトの名無しさん:2007/10/31(水) 10:34:22
Q:アラーの神とか、そういう慣用的というか比較的くだけた表現は原文でもよくわからないし
じゃあどうすればいいんだ?

A:無視
604デフォルトの名無しさん:2007/10/31(水) 12:12:07
Doubutu←Honyurui←Inu
            ←Neko
     ←Chorui  ←Suzume
            ←Karasu

このようなクラス階層のオブジェクトをポリモフィズムする場合...

std::vector<Doubutu*> doubutu_;
と保持して、HonyuruiやChoruiに純粋仮想と定義されたメンバ関数を呼び出す時はダウンキャストする。

ダウンキャストするぐらいなら最初から、
std::vector<Honyurui*> honyurui_;
std::vector<Chorui*> chorui_;
と保持する。

どちらがいいのでしょうか?
605デフォルトの名無しさん:2007/10/31(水) 12:17:24
そもそも継承するような種類のものだろうか。
606604:2007/10/31(水) 12:38:09
>>605
動物に例えたのがまずかったですかね。
HonyuruiとChoruiに共通の部分(仮想関数)がある場合、その部分を別のインターフェイス(Doubutu)として定義し、
継承することによって、HonyuruiやChoruiをDoubutuとして振舞う事も可能になり、便利だと思ったんですけど、
この多重継承事態がまずいですか?
607デフォルトの名無しさん:2007/10/31(水) 12:42:55
いや別に多重継承じゃないだろそれ。
608デフォルトの名無しさん:2007/10/31(水) 14:15:17
>>604
キャストしないほうが安全。いいか悪いかは自分で選べ。
609デフォルトの名無しさん:2007/10/31(水) 14:42:10
>>604
好きにすれば…としか。
ダウンキャストするなら、dynamic_cast 使えよ。
610デフォルトの名無しさん:2007/10/31(水) 17:23:46
マルチプラットフォームでGPLなどの制限がないフリーのC++コンパイラを探していますが、ありますか?
GCCはGPLがあってだめでした。
BCCはWin32しかコンパイラがなさそうでだめでした。
よろしくお願いします。
611デフォルトの名無しさん:2007/10/31(水) 17:55:20
>>610
それを手に入れてどうするつもり?
612デフォルトの名無しさん:2007/10/31(水) 18:04:05
export実装がんばれ。
613604:2007/10/31(水) 18:35:22
>>608,609
ありがとうございます。
どちらかが悪い方法というわけではないんですね。
614デフォルトの名無しさん:2007/10/31(水) 20:43:09
>>598
...のところは何か省略してる?
testは、「char型の要素数3の配列への参照を返す関数」。
違ってたらすまん。
615デフォルトの名無しさん:2007/10/31(水) 21:13:05
>>610
GCCのライセンスって、コンパイルしてできた出力には
GPLがかからないなんて例外事項が付いていなかったっけ?
616デフォルトの名無しさん:2007/10/31(水) 21:37:43
>>598
char 返し引数に ... を取る関数ポインタの3つの配列の宣言。
617デフォルトの名無しさん:2007/10/31(水) 21:47:15
char (&test[3](...))
そう言うならこれは?
618デフォルトの名無しさん:2007/10/31(水) 21:51:43
>>598
>char (&test(...))[3]
引数が...で、要素数3のchar配列への参照を返す、test関数……かな

>>617
>char (&test[3](...))
それってコンパイル通るのか?
分からん
619デフォルトの名無しさん:2007/10/31(水) 22:24:50
>>615
ふと思ったんだが、そういう例外事項がないと、
GPLなプログラムによって生成されたコンテンツはGPLになるのか?
たとえばエディタとかペイントソフトとか画像処理とか。
620デフォルトの名無しさん:2007/10/31(水) 22:29:21
http://kmaebashi.com/programmer/pointer.html
Cだけど、これは参考になるはず。

598はこうなる(614で既出)。
test is function returning reference to array of char
testはcharの配列への参照を返す関数

>>617
test is array of function returning reference to char
charへの参照を返す関数の配列
関数の配列だから、普通の変数としては存在できそうにないな。
621デフォルトの名無しさん:2007/10/31(水) 22:31:13
622デフォルトの名無しさん:2007/10/31(水) 22:34:16
>>619
それは derived work をどう解釈するかという形而上学的論争になるんじゃない?
エディタやペイントソフト程度なら、生成されたコンテンツは派生物にはならないと思うが、
emacs が生成した dump なんかは派生物になるだろうし。

緩める側への例外規定があれば、この論争を避けることができる。
623598:2007/10/31(水) 22:41:55
>>>char (&test(...))[3]
これboostスレに合ったんだよね
普通関数ポインタ/リファレンスならなら
char (*test[3])(...)とか、char (&test)(...)だよな・・・?とか思って助けてもらおうとおもった。
>>617
char (&test[3])(...)は通らなかった。

この関数を呼んでる場面もsizeof( test(NULL) )みたいにsizeofに掛けてたから、
>>618の言う通り要素数3のchar配列参照を返すっぽい。
こんな書き方始めてしったよ・・・
624デフォルトの名無しさん:2007/10/31(水) 22:52:00
テンプレートクラスについて質問があります。

テンプレートクラス側のメソッドから、
(返り値がテンプレート参照のメソッド)
不正な値を表すnullのような返り値を返したいのですが

その際の「nullのような返り値」をどう定義したものか困っております。

漠然と、const staticで定義した定数の参照を返すか?と考えているのですが
詰めきれていません。

いいやり方はないものでしょうか?
宜しくお願いします。

625デフォルトの名無しさん:2007/10/31(水) 22:55:13
横からだが、
もはやどんな関数ポインタが出ようが理解できるという自信があったのに、
char (&test(...))[3] は理解できなかった。
charへのキャストか? それでoperator & ()をオーバーロードしているのかも、じゃ[3]はなんだ? とか思ってしまった。
まさか配列への参照を返す関数だったとは。

typedef char (&test(...))[3] ;

typedef char ret_type[3] ;
typedef ret_type & same_type(...) ;

int main()
{
  std::cout << typeid(test).name() << std::endl ;
  std::cout << typeid(same_type).name() << std::endl ;
  std::cout << boost::is_same<test, same_type>::value << std::endl ;
}

うーん、人間コンパイラへの道は遠い。
626デフォルトの名無しさん:2007/10/31(水) 23:07:38
>>624
ポインタじゃ駄目なの?

>>625
char (&test(...))[3]みたいに出されると、
咄嗟に変数だと思っちゃうからねえ
627デフォルトの名無しさん:2007/10/31(水) 23:14:02
>>626
関数ポインタを引数に取る関数を、typedef使わないでってのは前に見たことがあったんだけど。
628デフォルトの名無しさん:2007/10/31(水) 23:17:04
>>625
&をいったん*に置き換えて考えてみたら、分かりやすかったんじゃない?
629デフォルトの名無しさん:2007/10/31(水) 23:19:53
>>626
今回はテンプレートの練習がてらに組んでる物なので、
テンプレートらしい解決法があればそちらを取りたい次第です
630デフォルトの名無しさん:2007/10/31(水) 23:23:48
>>624
うん、まさにポインタの出番だ
631デフォルトの名無しさん:2007/10/31(水) 23:25:44
>>629
その問題ってテンプレートは関係なくて、参照型を返すメソッドで
null相当の値を返したい、というのとはどこか違うの?
632デフォルトの名無しさん:2007/10/31(水) 23:27:59
>>624
ポインタをあたかも参照のように使えるラッパを書くとか。
で、is_valid()みたいなメンバ関数を付け加えるとか、
あるいは例外を投げるとか。

そもそも、例外投げていいような状況なら、ラッパなんて要らないがw
633デフォルトの名無しさん:2007/10/31(水) 23:38:26
>>631
型が決まっていればそれに対しての不正な値をひとつ決めればOKだと思うのですが、
テンプレで複数の型を扱う必要がある場合にどうするか、で悩んでます。

>>632
少し考えてはみたのですが、
そのテンプレがクラスのみではなく、char,int等の型も扱う場合に対処できるのでしょうか?
あと、基本例外はなしで考えてます。
精々printfぐらいで
634デフォルトの名無しさん:2007/10/31(水) 23:46:55
boost::optional的なモノを自作
635デフォルトの名無しさん:2007/10/31(水) 23:48:55
>>624
ポインタを使うのが妥当
不正な値を返すかどうかは実行時に決まるので
テンプレートでできることはない
テンプレートで解決できるのはコンパイル時の問題
636デフォルトの名無しさん:2007/11/01(木) 00:04:07
typeid(type).name() で出力される文字列はそのままコンパイライライライライライライライライライライライライライラに通してエラー無くコンパイルできる事が保証されているんでしょうか?
637デフォルトの名無しさん:2007/11/01(木) 00:04:41
>>634
boostは触ったことがなかったのですが、
かなり参考になりそうです。

>>635
> 不正な値を返すかどうかは実行時に決まるので
> テンプレートでできることはない
> テンプレートで解決できるのはコンパイル時の問題

なるほど、わかりやすいレスありがとうございます。
テンプレで全部まかなうっていうのは無理がありそうですね。

とりあえず、>>634氏のおっしゃるように、boost::optionalを目指して何か作ってみようと思います。

皆さん、相談にのっていただいてありがとうございました。
638デフォルトの名無しさん:2007/11/01(木) 00:11:37
>>636
つ 牛乳
639デフォルトの名無しさん:2007/11/01(木) 00:21:49
>>636
なにも保障されていない。
NULL終端されてるシングルバイト文字列か、あるいはマルチバイト文字列かもしれない。
とりあえず人間が読んで、どんな型なのか分かる文字列であることが期待されているだけ。
640デフォルトの名無しさん:2007/11/01(木) 00:30:25
>>639
type_info::name()はconst char *を返すことが決まっているから、
その型にあったコーディングさえしていれば、コンパイルはできるんじゃない?
(文字列の内容をどう扱うか、どう表示させるかはともかく。)
636が言う、コンパイラに通すの意味が良く分からんが。
641デフォルトの名無しさん:2007/11/01(木) 01:27:52
>624
「テンプレートらしく」ということなら、不正通知をポリシーに切り出して、組替え可能にするんじゃない?
そうすれば「例外」「ヌルポインタ」「ヌルオブジェクト」「その他」を好きなように切り替えられるようになるし。
642デフォルトの名無しさん:2007/11/01(木) 01:59:09
まず、配列への参照ってのが普段あんまり使わんな・・・
643デフォルトの名無しさん:2007/11/01(木) 02:34:44
ポインタだと無理だけど、参照だとテンプレートで配列のサイズが特定できる。
あまり使う場面ないけど
644デフォルトの名無しさん:2007/11/01(木) 06:07:05
Boost.Rangeでは、ところどころに使っていそう。
645デフォルトの名無しさん:2007/11/01(木) 07:40:33
boostにreference_holderとかあったような
これとコンテナテンプレート使えば参照のコンテンが作れる
646デフォルトの名無しさん:2007/11/01(木) 09:03:44
>>640
コピペして貼り付けてコンパイル
VC8 でやってみて void (__thiscall type::func)(void) の様なものが現れた時にそれをメンバ関数ポインタの型だと思ってコンパイルに通しても
駄目でしあt
647デフォルトの名無しさん:2007/11/01(木) 13:17:55
>>646
ネタにマジレスとかw
648デフォルトの名無しさん:2007/11/01(木) 14:31:28
>>643
kwsk
649デフォルトの名無しさん:2007/11/01(木) 14:57:40
あれ、何故か出来ない。

typedef int (&foo(...))[3] ;
typedef int (&bar(int))[3] ;

//コンパイルエラー
//typedef boost::function_traits<foo>::result_type ret ;

typedef boost::function_traits<bar>::result_type ret ;
std::cout << typeid(ret).name() << std::endl ; // int [3]
typedef boost::extent< ret > size ;
std::cout << size::value << std::endl ; // なぜか0
650デフォルトの名無しさん:2007/11/01(木) 15:29:57
こんなのとかか?
template<typename T, std::size_t N> inline std::size_t numberof(T (&)[N]) {return N;}
651デフォルトの名無しさん:2007/11/01(木) 15:57:12
>>649
その場合retは参照型になるようだ
参照型やポインタの場合boost::extentは0になるのは正しい動作の筈
対策としてはremove_referenceで参照を取り除いてやること
boost::remove_reference<boost::function_traits<bar>::result_type>::type ret
652デフォルトの名無しさん:2007/11/01(木) 16:07:33
余裕があったらsvn headのboost::function_typesも使ってやってくだしあ
653649:2007/11/01(木) 16:23:32
>>651
いや、それは真っ先に思いついたので既に試した。
それでも0が表示される。
VC8なんだが何故だろう。
654デフォルトの名無しさん:2007/11/01(木) 16:25:11
template<std::size_t N> int &ar(int *array)[N]{
return *array;
}
655649:2007/11/01(木) 16:27:30
うげ、remove_referenceという、メタ関数を「呼び出す」のを忘れていたorz
656デフォルトの名無しさん:2007/11/01(木) 17:57:40
>>654
コンパイル通らないよ・・・?
657デフォルトの名無しさん:2007/11/01(木) 19:03:11
左辺値、右辺値がよくわかりません!
特にウヘンチサンショウっていう奴。
C++に限ったことじゃない?
658デフォルトの名無しさん:2007/11/01(木) 19:13:53
左辺値=変数
右辺値=値
659デフォルトの名無しさん:2007/11/01(木) 19:21:38
>>658
const値は?
代入可能な左辺値と単に左辺値と言った場合の違いは?
660デフォルトの名無しさん:2007/11/01(木) 19:35:42
左辺値は実体がある=メモリを食ってる=アドレスを得ることが可能。
右辺値はそれ以外の全て。
定数であることとは関係ない。
例えば、関数は左辺値。
661デフォルトの名無しさん:2007/11/01(木) 19:35:53
>>654
やりたいのはこういうこと?
#include <iostream>
//#include <boost/mpl/identity.hpp>

template<std::size_t N, typename T>
T (&ar(T* array))[N]
//typename boost::mpl::identity<T (&)[N]>::type ar(T* array)と書くほうがまだ分かりやすいと思う
{
  return reinterpret_cast<T (&)[N]>(*array);
}

const int N = 1024 * 1024;

class hoge
{
public:
  ~hoge()
  {
    std::cout << "~hoge" << std::endl;
  }
};

int main()
{
  typedef hoge my_array_t[N];
  my_array_t& a = ar<N>(new my_array_t);

  delete[] &a[0];
}
662デフォルトの名無しさん:2007/11/01(木) 19:54:30
>>660
一時オブジェクトもメモリを食ってるけど。
配列型も左辺値だけど変更可能な左辺値ではないよね。
int a[ ] の場合aも左辺値
663デフォルトの名無しさん:2007/11/01(木) 19:57:24
代入構文の左辺になれるものとかw
664デフォルトの名無しさん:2007/11/01(木) 20:05:59
俺は適当に>>663の様に考えてた
厳密な定義を考えた事ないや
665デフォルトの名無しさん:2007/11/01(木) 20:09:53
>>663
Cならその解釈でいいんだけども。
666デフォルトの名無しさん:2007/11/01(木) 20:20:45
>>662
一時オブジェクトは生成の省略が許されているから、
必ずメモリを食うとは限らない。
っていうか必ず食ったら嫌すぎる。
よって右辺値扱いで正解。
667デフォルトの名無しさん:2007/11/01(木) 20:38:31
でもなぜかアドレスが取れてしまう不思議
それともVC7.1がウンコなだけだろうか
668デフォルトの名無しさん:2007/11/01(木) 20:43:32
gccなんてラベルのアドレスも
669デフォルトの名無しさん:2007/11/01(木) 21:22:17
>>660
関数が左辺値ってどういうこと?
C++に関数という値はないんじゃない?
670デフォルトの名無しさん:2007/11/01(木) 22:58:22
>>669
関数が左辺値かどうかは知らないが、
少なくとも、アドレス演算子や暗黙の変換で、関数からは関数へのポインタを得ることが可能。
>>662のように配列と同じく関数は変更不能な左辺値なのかもしれない。

>>667
ウンコ。でも警告レベルを上げれば警告になったはず。
671デフォルトの名無しさん:2007/11/01(木) 23:12:27
もちろん関数へのポインタはあるよ
それはポインタだから左辺値にもなるし右辺値にもなる

でも>>660には関数が値だと書いてあるのでどういうことだろうと

プログラミング言語の話をするときには関数自体と関数へのポインタは
明確に区別するべきだと思うし

まあ、言葉のあやのような気もするけど
672デフォルトの名無しさん:2007/11/01(木) 23:20:06
関数へのポインタ型とは別に、関数型があるという点で、
C/C++には、そういう意味での関数があると俺は思っている。
関数型のリテラルが書けないとこをつかれたら痛いけど。
673デフォルトの名無しさん:2007/11/01(木) 23:26:05
>>671
そこでいう関数は、関数名のことかな。
int a; という変数があるとして、変数名aを左辺に書けばそのオブジェクトを表すし、右辺として評価すればその値は変数の内容。
同様に、関数名を評価した値は関数のアドレスだけど、関数名自身は左辺値になる。まあ代入はできないけど。
674デフォルトの名無しさん:2007/11/01(木) 23:32:01
>>671
まぎらわしいが、「左辺値」とは「値」のことではい「式」のことだ。
オブジェクト参照を生成する式とか、結果としてアドレスを割り出せる形になる式のことだ。
675デフォルトの名無しさん:2007/11/01(木) 23:34:12
やっべC++暦2年だけど今の流れサッパリわかんね
インターネッツで修行してくる
676デフォルトの名無しさん:2007/11/01(木) 23:35:32
typoった
はい → ない

「関数そのもの」と「関数コール」と「関数ポインタ」と「関数名」って
どれも違うことなんだけど難しいねえ
677671:2007/11/01(木) 23:37:20
ああそうか
関数へのポインタ fp があるということは

*fp

は関数への参照、つまり左辺値なんだね
なるほど、わかりました
678デフォルトの名無しさん:2007/11/01(木) 23:43:14
そう考えると関数定義ってコンパイラから見ると
const staticなポインタ変数に初期値を与えてる感じなのかな
679デフォルトの名無しさん:2007/11/01(木) 23:59:30
>>657が右辺値参照と言っているが、
それ自体は、右辺値で初期化できる参照型の1種であるというだけ。
従来の参照型はもちろん左辺値参照にあたる。

左辺値参照の初期化は左辺値でなければならず、
右辺値参照の初期化は右辺値(左辺値→右辺値変換はだめ)でなければならない。
(というとかなり語弊がありまくりだけど気にしない)
何が右辺値で何が左辺値かはここまで散々議論されてきたので上のほうを見ろ。

右辺値はどうせすぐに消えるのだから、
消える前に中身をぶっ壊してもいいだろというのが右辺値参照導入の動機。
時と場合によって、バカ正直な深いコピーをする必要がなくなる分、高速化に繋がるというわけ。
680デフォルトの名無しさん:2007/11/02(金) 00:02:14
> 右辺値参照の初期化は右辺値(左辺値→右辺値変換はだめ)でなければならない。
なんだ、すげえ真っ当な仕組みなんだな。
もっとトンデモな仕様想像してたよ俺。
681デフォルトの名無しさん:2007/11/02(金) 00:08:04
仕事で初めてC++でWindowsアプリを作ることになりました
内容的にはWEBアプリでこれまでやっていたことを、
クライアントアプリに移すような作業で、製作環境はVisualC++2005になります

そこでお尋ねしたいのですが、C++を使用する場合に、
今の流行として、CLI、MFC、標準ライブラリとSTL、
これらのうち、どれを使用するのが適当なのでしょうか?
682デフォルトの名無しさん:2007/11/02(金) 00:11:11
具体的な内容がわからんとなんとも言えない
683デフォルトの名無しさん:2007/11/02(金) 00:11:23
なんでもありのバーリトゥードがC++の醍醐味
684デフォルトの名無しさん:2007/11/02(金) 00:16:02
元がWEBアプリならhtaという選択肢はなし?
スレ違いだけど
685デフォルトの名無しさん:2007/11/02(金) 00:16:32
戻り値が正しくない演算子多重定義だけど(メイヤーズ本)

T operator+(const T& lhs, const T& rhs) ;

の場合、

T t1, t2, t3;

t1 + t2 = t3 ;

が可能になる。t1 + t2 は一時オブジェクトすなわち右辺値を生成するのに
代入可能なのが気持ち悪い。
686デフォルトの名無しさん:2007/11/02(金) 00:21:12
戻り値を const T にするのではダメ?
687デフォルトの名無しさん:2007/11/02(金) 00:28:41
ご回答、ありがとうございます

>>682
あまり詳しい内容はアレなんですが、何かを登録するシステムで、
画面数が10くらいで、セレクトボックスとテキストボックスがあって、
検索と登録を行うみたいな感じです
クライアントアプリにしてUIリッチにしてオペレータの作業時間を短縮したいそうです
主にドラッグ&ドロップで登録するオブジェクトをぽんぽん追加したいようで

>>683
なんでもアリ過ぎて、腕を取りにいくべきかパウンドで攻めるべきか、
マウントポジション取ったまま悩んでいます

>>684
htaは初耳でした。少し調べてみます
688デフォルトの名無しさん:2007/11/02(金) 00:29:31
いや、お前ら、>>681はどのくらい役に立つかとか、そういうことを聞いてはいないぞ。
「今の流行」を聞いているんだ。

さて、そうだなぁ、MFCなんて昔はやった過去の遺物だろ。
確かに便利ではあるんだが、実装が古臭い。
もちろん、昔はまともなC++コンパイラがなかったから仕方ないんだが。

標準ライブラリとはおそらくはCのことだと思うが、これなんか古すぎて、
ほとんどのものが、いまどきは使用を推奨されないな。
だからVCにはセキュリティを考慮したバージョンが存在するわけで。

STLも、かなり荒削りなんだよね。C++の規格制定のギリギリになんとか作ったわけで、
考慮が足りない部分とか、そもそも未完成なものとかもある。

CLIだが、なんか微妙だよね。
わざわざC#を覚える必要がなくなれたC++の文法で使えるぐらいの利点しか。

あれ、今の流行のライブラリは見つからないな。
689デフォルトの名無しさん:2007/11/02(金) 00:29:34
ATL/WTLが最近の流行。ただしマイブームに過ぎないけど。
690デフォルトの名無しさん:2007/11/02(金) 00:31:32
ATL, WTLをboostと組みあわせて使うのがなかなか無間地獄っぽくて楽しいかも
691デフォルトの名無しさん:2007/11/02(金) 00:35:25
>>688
標準ライブラリとはiostreamとかのことを言いたかったのでは?
それならそれで標準C++にとっては標準ライブラリ⊃STLだが。

いずれにせよ、GUIとは関係ない内容で、
681の挙げた他の選択肢とは、排他的なものではない。
692デフォルトの名無しさん:2007/11/02(金) 00:38:14
なあ。組み込みでCやってきてて、C++使うことになって、勉強始めたんだが。
STL使おうとしてる。

んで、まずは配列の代わりにvector使うのが良いと聞いて、使おうとしてるんだが。
vectorの要素は、メモリ上に連続で並んでいることがわかって
一安心(効率のいいmemcpy使って一気に書き換えられるし)。

だが。push_back()するたびに、メモリの動的確保するってどうなんよ?
目を疑ったわけだが。vectorが使用するメモリ領域を上位で指定するとかして、
動的確保が発生しないようにする方法ってないんかね。
693デフォルトの名無しさん:2007/11/02(金) 00:40:58
つvector<T>::reserve(std::size_t)
694デフォルトの名無しさん:2007/11/02(金) 00:42:51
>>692
>動的確保が発生しないようにする方法ってないんかね。
あるよ。
std::vectorのメンバ関数をひととおり眺めてみれば?
695デフォルトの名無しさん:2007/11/02(金) 00:45:07
>>691
Windowsアプリといっているだけで、なにもGUIのライブラリに限定しているわけじゃないだろ。
GUIのライブラリも重要だが、それ以外にもやることはあるだろ。
696デフォルトの名無しさん:2007/11/02(金) 00:47:59
>>692
まあ、普通はメモリが足りなくなったら、
現在のサイズ1.5倍とか2倍とか確保して、
毎回メモリ確保しなくてもいいように実装するんだけどな。
697デフォルトの名無しさん:2007/11/02(金) 00:54:47
商用ならQtにすれば?
698デフォルトの名無しさん:2007/11/02(金) 00:55:05
>>693,694
ありがとう、ありがとう。

ちなみにman vectorしてもなにもでてこないのだけど、STLの
APIリファレンスってどうやったら見れるのかな?Linux使ってます。
Webのやつ見てるけれど、イマイチわからないのです。

http://www.wakhok.ac.jp/~sumi/stl/header/vector.html#constructor

reserve()すると、size()で返る要素数がreserve()で指定したものに
なってしまうのかな?
699デフォルトの名無しさん:2007/11/02(金) 00:59:40
>>698
resize(), capacity()についても調べてみると幸せになれるよ。
700デフォルトの名無しさん:2007/11/02(金) 01:00:05
reserveはcapacityを増やすだけでsizeは変わらない
701デフォルトの名無しさん:2007/11/02(金) 01:05:25
>>700
ありがとう!

ちなみに、STLのリストやらキューやらで、要素を追加すると
同じようにメモリの確保が発生するのかな??
702デフォルトの名無しさん:2007/11/02(金) 01:05:54
resize 実際にsizeが変更される
reserve これで指定したサイズまではメモリ確保がされない
だと思う
703デフォルトの名無しさん:2007/11/02(金) 01:06:53
それと、vectorやらlistやqueueで、要素を追加するときに、
allocが発生しない、かつメモリコピーも発生しないように
することってできますか?
704デフォルトの名無しさん:2007/11/02(金) 01:08:08
>>702
ありがとう!

703の追記ですが、上位で指定した領域をそのままリストにつなぐという
意味です。vectorだとコピーせざるを得ないですが。
705デフォルトの名無しさん:2007/11/02(金) 01:10:07
出遅れた('ー`)
Object Poolとかでググると幸せになれるかもしれない。
706デフォルトの名無しさん:2007/11/02(金) 01:11:42
>>703
listやqueueにはvector::reserve相当の関数はないから、
自前でアロケータを書けばいいのかも。
707デフォルトの名無しさん:2007/11/02(金) 01:20:53
>>705
Object Pool検索しましたが、Javaのしかでてきません!

>>706
自前でアロケータ書いて、ごちゃごちゃやるくらいなら、
独自高速版STLもどき作ったほうが、幸せになれるような
気がするなぁ・・・。
708デフォルトの名無しさん:2007/11/02(金) 01:22:36
>>704
list についてはあらかじめ作っておいた別の list から splice() でつなぐことができる。
メモリ確保についてはタイミングが変わるだけなんだけどね。
709デフォルトの名無しさん:2007/11/02(金) 01:24:16
>>707
標準のSTL自体がそれなりにチューニングして実装されているだろうから
まずはそれで本当に遅いのかを確認したほうが良いのでは?

がんばって独自版を実装してみたものの実は不要だった、なんて
不幸せになるような気がするなぁ…。
710デフォルトの名無しさん:2007/11/02(金) 01:30:42
>>706
手軽に済ませたいならboost::poolがあるよ
711デフォルトの名無しさん:2007/11/02(金) 01:32:46
>>708

おぉ、シリマセンデシタ。ありがとうございます。

>>709
allocしない、かつコピーを最小限の機能限定STL(自動的にvectorを伸張しない)
とかだったら、アプリによっては数倍の速度になるんじゃないかなぁ。

リストもキューも、本質的には単なるポインタの付け替えなわけだし。
それを渡された要素分、allocしてコピーしてたら速度の違いは歴然
じゃないかな。組み込みでは。
712デフォルトの名無しさん:2007/11/02(金) 01:45:31
ていうか、あなたの使うSTLのallocatorの実装はpoolを使ってないの?
大抵の実装がsetやlist等の必然的に細切れになるコンテナ用に
poolを使ったallocatorを用意していたと思うんだけど
713デフォルトの名無しさん:2007/11/02(金) 01:58:31
>>711
「じゃないかな」なんてつくようなら、まずは何も考えずに使ってからにしたほうがいいよ。
処理系実装者を一度ぐらい信じてやってもいいでしょ。

allocator をカスタマイズしたり、自作の vector や list を正しく作るのはほんとうに
大変なんだよ。
714デフォルトの名無しさん:2007/11/02(金) 02:48:09
>>712,713
allocの処理負荷を軽減できるというのはわかるけど。
メモリコピーは、そうやっても減らないわけだし。

アプリ処理の2〜3割を、メモリコピーが占めることが
Cですらザラにあるわけで。
715デフォルトの名無しさん:2007/11/02(金) 02:52:54
あのー、setやlistは、vectorみたいにデータが移動しないことが要件に含まれているんですけど
716デフォルトの名無しさん:2007/11/02(金) 03:26:40
>>714
コピーの処理時間が問題になっているのがわかってから考えるんだ。
さらに言うと、問題になっている箇所以外は標準コンテナのままでいい。

偉い人も言っている。 "Premature optimization is the root of all evil" と。
717デフォルトの名無しさん:2007/11/02(金) 03:26:59
ほんとに頭悪くてごめん。
右辺値参照が理解できん。
718デフォルトの名無しさん:2007/11/02(金) 03:34:57
>>717
これでどう?

// 既存の(左辺値参照用)コピーコンストラクタ
vector::vector(vector const& other)
{
 allocate(other.size());
 // コピーうぜー。けど other は const& だからしょうがないんだぜ。
 copy(other.begin(), other.end());
}

// 右辺値参照用コピーコンストラクタ
vector::vector(vector&& other)
{
 // other つぶしていいんならメモリ確保もコピーもいらねー。うはwwww
 other.swap(*this);
}
719デフォルトの名無しさん:2007/11/02(金) 10:02:08
>>718
const 参照は右辺値を参照できるけど、左辺値は参照できない。
vector const& otherのほうが右辺値参照ではないの?
720デフォルトの名無しさん:2007/11/02(金) 10:09:24
>>702
reserveはメモリ確保はされるけど初期化はされない
ということじゃないか?
resizeはメモリ確保されて初期化もされるから要素数も変更される
721デフォルトの名無しさん:2007/11/02(金) 10:40:30
>>718
これは便利!と思ったけど調べてみたら、これできるのC++0xからなのね。
722デフォルトの名無しさん:2007/11/02(金) 12:01:12
>>719
そこらへんやオーバーロード解決のルールも変更されて、右辺値を引数にした場合は
右辺値参照用のほうが優先されるんだろ。
723デフォルトの名無しさん:2007/11/02(金) 12:06:59
CHAR_BIT は最低 8 ビットで char が符号付か符号無しかは処理系定義だから
一般的に std::ostream の put() は 0 から 127 までしか書き込めませんか?
0 から 255 まで書き込むには std::ostream<unsigned char> を使うのでしょうか?
724デフォルトの名無しさん:2007/11/02(金) 12:31:46
>>723
何がしたいのかわからん。
移植性を優先するなら std::ostream に int を出し入れするのがいいんじゃないの?
725デフォルトの名無しさん:2007/11/02(金) 12:57:35
>>724
すみません。すでにフォーマットが確定したバイナリデータを書き込むときのはなしです。
フォーマットでは1バイトが8ビット符号無し整数です。
726デフォルトの名無しさん:2007/11/02(金) 13:15:47
>>725
typedef unsigned char uint8;
といったようにtypedefしておき、処理系によってこの定義を変える
727デフォルトの名無しさん:2007/11/02(金) 13:23:14
>>723
std::ostream<char>は必ずしも8bit cleanではないのではないかってこと?
規格上どうだか、俺は知らないなあ。
charが符号付きであっても、↓が動かないような環境は、見たことが無いけど

#include <iostream>
int main()
{
    const char *s = "こんにちは、世界\n";
    char c;
    while (c = *s++)
        std::cout.put(c);
}
728727:2007/11/02(金) 13:23:45
std::basic_ostream<char>だな、すまん
729デフォルトの名無しさん:2007/11/02(金) 13:45:03
s の型が std::ostream<char> で char が表現できる範囲が
-128 から 127 のとき

s.put( 200 );

を実行すると 200 がどういう数値変換されるかは処理系定義
だと思っています。
128 以上はすべて 0 に変換される処理系もあるかもしれません。
730デフォルトの名無しさん:2007/11/02(金) 14:07:06
>>725
C++ の規格にストリーム出入力の規定はなくて C のライブラリの上に被さってる。
C の規格によるとストリームは character の順序つき列だとされている。
character が char を指すとして、 CHAR_BIT が 8 でない環境で 8 ビット符号なし整数
というバイナリデータを書き出すこと自体が不可能だろう。たぶん。

で CHAR_BIT が 8 だとして符号有り無しの話だけど、 unsigned char の変数を
char* で指して読み出した値を put() すればいいよ。 C/C++ の (signed/unsigned) char* は
任意のバイト列を指すことができるとされているからね。整数変換を通してしまうと
>729 の言うように処理系定義でどうなるかわからない。
731デフォルトの名無しさん:2007/11/02(金) 14:46:58
unsigned char のオブジェクトを signed char へのポインタを通して
アクセスしたときはどのような動作になるんでしょうか。
負の整数を2の補数以外で表現する処理系では unsigned char の 255 が
signed char の 0 として取得されるようなことはないでしょうか?
732デフォルトの名無しさん:2007/11/02(金) 17:24:49
>>718
vector::vector( vector const &other ){
 array_ptr = other.GetArrayPtr();
}
って右辺値参照用コピーコンストラクタと同じ感じじゃないの?
733デフォルトの名無しさん:2007/11/02(金) 19:32:18
dir0/file0.cxxの中で
#include <dir1/file1.h>
#include "dir2/file2.h"
としたとき、および、dir2/file2.hの中で
#include "dir3/file3.h"
としたとき、それぞれincludeされるファイルの探索範囲・順序は、標準では決められてないのでしょうか?
また、主要コンパイラでの探索範囲・順序などご存じありませんか?
mingw gcc 4.3.2では
<> → includeパス
"dir2/file2.h" → dir0/dir2/file2.h
file2.h中で"dir3/file3.h" → dir0/dir3/file3.h
734デフォルトの名無しさん:2007/11/02(金) 19:41:58
>>733
(a) #include <...>は、実装依存の一連の場所(*1)から探す。
(b) #include "..."は、まず実装依存の一連の場所(*2)から探し、その後(a)と同様にして実装依存の場所から探す。

古いCだと、(2)でまず探すのが元ソースのディレクトリになっていた。
C++でもそういう実装が多いと思うけど、決まっているわけじゃない。

ディレクトリの考え自体が実装依存だから、それ以上のことは決まっていないみたい。
735デフォルトの名無しさん:2007/11/02(金) 21:37:08
>>719
今でもconst参照は左辺値を参照できるぞ、右辺値「も」参照できるというだけで。

提案では、722の言うとおり718のコードで右辺値を渡すと
const左辺値参照よりも右辺値参照を優先して解決される。
736デフォルトの名無しさん:2007/11/02(金) 22:09:09
>>735
勘違いしてた。
非const参照では右辺値を参照できないと言いたかった。
vector&& otherの&が二個あるのが右辺値参照を表してると思っていいの?
初めて見る構文だから
737デフォルトの名無しさん:2007/11/02(金) 22:39:43
>>736
そういうこと、&&が右辺値参照を意味する。
C++0xでもconstな左辺値参照は相変わらず右辺値を参照することも可能になっていて、
だから、既存の右辺値参照を考慮していないプログラムの互換性も保てるとされている。
738デフォルトの名無しさん:2007/11/02(金) 23:25:09
>>737
なるほど
どんどん仕様は拡張されてるわけね
まだまだおいつかないわ
739デフォルトの名無しさん:2007/11/02(金) 23:28:39
>>734
ありがとうございます
VC++やBorland C++ではmingwと違った感じになるか、ご存じでしょうか?
boostライブラリでは、一部は"boost/〜/〜.hpp"みたいにincludeしてることもあるようですから
国際標準で定まってなくても、デファクトなやり方があるのかなと期待しつつ。
740デフォルトの名無しさん:2007/11/02(金) 23:33:21
void func(const int &v){ &v; }
func(0);

これって規格上通るの?
741デフォルトの名無しさん:2007/11/02(金) 23:47:37
>>739
VC++、BCC、GCCなどといったパソコンで動くコンパイラだと、
734の(*1)にあたる場所は、コンパイラオプションや環境変数で指定したディレクトリで、
(*2)はソースファイルのあるディレクトリと思っていて構わない。
742デフォルトの名無しさん:2007/11/02(金) 23:50:04
>>740
もちろん問題ない。
funcを呼ぶ側にとっては一時的な右辺値でも、
funcの中の人にとってはfunc内を実行している間ずっと存在し続ける左辺値(constだけど)。
743デフォルトの名無しさん:2007/11/03(土) 00:07:43
>732
それによって初期化された vector が破棄されるときと、other が破棄されるときを考えてみよう。
744デフォルトの名無しさん:2007/11/03(土) 00:19:34
>>742
これをint*にキャストしても規格上通る?
745デフォルトの名無しさん:2007/11/03(土) 07:06:51
void func(const int &v){ const_cast<int*>(&v); }
ならいいと思われる
746デフォルトの名無しさん:2007/11/03(土) 08:16:29
実際に中身を書き換えなければ、constのないポインタ型へ変換したり、
そこから参照剥ししたりしても規格上問題ないはず。
747デフォルトの名無しさん:2007/11/03(土) 17:51:17
char* buffer
にCreateFileなどでファイルの文字列を一気に読んで
それをstrtok_sで分割し、とっておきたいとします。

char* hoge = strtok_s(NULL,delim,&nexttoken);
char* hage = strtok_s(NULL,delim,&nexttoken);
int sage = atoi(strtok_s(NULL,delim,&nexttoken));

そして、読み込み&分割が終わった後に
delete[] buffer
と、後始末をすると、int sageなどはコピーされてるので消えませんが、
hoge hageに関してはポインタなので一緒に消えてしまいます。
コピーをとっておく場合はどうやって書いたらいいんでしょうか?

ちなみに、
char hoge[256];
strcpy(hoge,strtok_s(NULL,delim,&nexttoken));
とか
char hoge[256];
sprintf(hoge,strtok_s(NULL,delim,&nexttoken));

などとやってみたんですが、内容がフフフフの連続のようになってしまいました。
正しくはどうやって書いたらいいですか?
748デフォルトの名無しさん:2007/11/03(土) 18:00:24
なぜstrtok_sは使うのにstrcpyなんだ。
strtokよりよっぽど重要だぞ。

第一それ、バッファオーバーフローするだろ。
749デフォルトの名無しさん:2007/11/03(土) 18:13:33
>>747 初心者スレに帰ってくれ。
750デフォルトの名無しさん:2007/11/03(土) 18:35:37
テンプレート関数についてです。
テンプレート関数はオブジェクトファイルにする時点でテンプレートの部分が実体化(?)している必要がありますが、
もしテンプレート関数を使用するファイルを個々にオブジェクトファイルにしてから結合したい場合、
テンプレートクラスの場合は
template MyClass<int>;
のようにすれば解決できるようですが、テンプレート関数の場合はどのように宣言すればよいのでしょうか?
751デフォルトの名無しさん:2007/11/03(土) 18:38:20
>>748
そこって本質ですか?
strtokでもらうのは最初のbufferの中でデリミタに区切られたところのポインタですよね?
当然、後片付けでbufferをdeleteしてしまえば、
そのhoge hageの指し示している先の内容も消されてしまうというのは理解できます。
一方、int sageはatoiでコピーをもらってるので消えません。
要するに文字列の「コピー」をもらいたいんですが、書き方が分かりません。
752デフォルトの名無しさん:2007/11/03(土) 18:44:57
>>750
ん?同じことができるでしょ?
やってみたなら、どうやったのかとエラーメッセージをどうぞ。
753747:2007/11/03(土) 18:58:48
class Holder{
public:
int kazu;
char* moji;

void print(){ printf("整数 = %d, 文字列 = %s \n",kazu,moji); }
};
void main(){
HANDLE file = CreateFile(
"test.txt",GENERIC_READ, FILE_SHARE_READ, NULL,
OPEN_EXISTING, FILE_ATTRIBUTE_READONLY, NULL);

DWORD size = GetFileSize(file,NULL);//ファイルサイズ
char* buffer = new char[size+1];
buffer[size]='\0';
DWORD read_size;//バッファに一気読み
ReadFile(file, buffer, size, &read_size, NULL);
CloseHandle(file);//ファイルクローズ

char delim[] = ",";
char *nexttoken;

Holder holder;
holder.kazu = atoi(strtok_s(buffer,delim,&nexttoken));
holder.moji = (strtok_s(NULL,delim,&nexttoken));

delete[] buffer;//←deleteしなければうまく動く

holder.print();
}
754デフォルトの名無しさん:2007/11/03(土) 19:00:03
>>751
strtokが失敗しているんじゃないか?
C++の質問でも回答でもないけど
755デフォルトの名無しさん:2007/11/03(土) 19:05:52
自分で答えは分かってるじゃない
delete[] buffer;//←deleteしなければうまく動く

holder.print() が参照する先が有効でないといけないだけ
756デフォルトの名無しさん:2007/11/03(土) 19:06:43
char *s = strtok_s(NULL,delim,&nexttoken);
header.moji = new char[strlen(s) + 1];
strcpy(header.moji, s);

delete[] buffer;

holder.print();
delete[] holder.moji;
}
757デフォルトの名無しさん:2007/11/03(土) 19:07:13
>>750
明示的特殊化の話?
それともexportの話?
758デフォルトの名無しさん:2007/11/03(土) 19:08:13
>>755
はい。ですから参照する先を取っておくんじゃなくて
内容をコピーしておくにはどうしたらいいんでしょうか。
759デフォルトの名無しさん:2007/11/03(土) 19:15:49
>>758 初心者スレに帰ってください。おねがいですから。
760デフォルトの名無しさん:2007/11/03(土) 19:21:24
>>758
必要な文字数を計算した後、strncpy。
\0が無いのでstrcpyは駄目。
761デフォルトの名無しさん:2007/11/03(土) 19:21:35
>>756
できたみたいです。ありがとうございました。

>>759
死ね役立たず。
人の足引っ張って楽しいかゴミクズ。
今すぐ死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。v死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
762デフォルトの名無しさん:2007/11/03(土) 19:23:37
マルチな上にスレ違いの質問で粘ったあげく、これかよ
763デフォルトの名無しさん:2007/11/03(土) 19:23:48
まぁ、あれだ。平和になってよかったじゃないか。
764デフォルトの名無しさん:2007/11/03(土) 19:24:54
>>761
死ね役立たず。
人の足引っ張って楽しいかゴミクズ。
今すぐ死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。v死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
765750:2007/11/03(土) 19:25:04
>>752
>>757
exportの方です。
そもそも、宣言の仕方がはっきりと分からないのですが。。
ヘッダと.ccファイルを別けているので、.ccファイル内で
template (返り値) (クラス名)::(テンプレート関数名)<(テンプレートに適応したい型)>;
でいいのでしょうか?
template Gtk::SpinButton* PController::newParameter<double>;
766デフォルトの名無しさん:2007/11/03(土) 19:28:04
>>765
export 関係あるか?

関数テンプレートの明示的特殊化なら引数リストも書かないと駄目だと思うよ。

あと、「いいのでしょうか?」って聞く前に自分で試してほしい。
767766:2007/11/03(土) 19:28:58
明示的特殊化じゃなくて明示的実体化だね。ごめん。
768デフォルトの名無しさん:2007/11/03(土) 19:40:33
exportってテンプレートの定義をヘッダーではなくソースに書く方式だけど

ヘッダー
//sample.h
template<class T> int func(T a);

ソース
//sample.cpp
#include "sample.h"
export template<class T> int func(T a)
{
 //定義
}

利用するソース
#include "sample.h"

void widget()
{
 //fを呼び出す処理など
}

てな感じになるんでは?
769デフォルトの名無しさん:2007/11/03(土) 19:43:34
>>762
マルチ?ちゃんと断ってるだろ。
しかもスレ違いってC++はCも含むだろ。
シネよ基地外。
770デフォルトの名無しさん:2007/11/03(土) 19:51:36
>>765
メンバ関数のことかな?
template <class T> Widget { };
template class Widget<int> //クラステンプレートの明示的具現化の宣言
template void Widget<int>::f(int); //メンバ関数A<T>::f()の明示的具現化の宣言
みたいになるかな

template (返り値) (クラス名)::(テンプレート関数名)(パラメータリスト);
かな

あと、関数テンプレートの場合、引数演繹に頼らないで明示的に
パラメータの型を指定するのは呼び出し時じゃね?
771770:2007/11/03(土) 19:52:37
以下訂正

//メンバ関数A<T>::f()の明示的具現化の宣言    ×
//メンバ関数Widget<T>::f()の明示的具現化の宣言 ○
772デフォルトの名無しさん:2007/11/03(土) 19:52:59
含むというのはスーパーセットのことですか^^;
773デフォルトの名無しさん:2007/11/03(土) 19:55:04
>>769
だったらCのスレなんかいらないだろカス
774デフォルトの名無しさん:2007/11/03(土) 20:21:36
>>773
Cのスレで「C++にしか含まれない」文法の質問をしたら
スレ違いというのは妥当だが
C++のスレで「Cにも含まれる」文法の質問したからって
スレ違いってことはないだろうよ。
775デフォルトの名無しさん:2007/11/03(土) 20:37:44
>>773
C使いのC限定の質問にC++で返答するわけにはいかんだろ。
よってCスレは必要。カスはお前な。
776750:2007/11/03(土) 20:47:19
>768
GCCのg++はexportに対応していないようなので使えませんでした。

>>766
聞き方が良くなかったようです。。
聞く前には当然自分で試行錯誤しています。実は今日一日中試行錯誤しています。。

>>770
クラスは普通のクラスだったので、
template void MyClass::method( double* );
のようにしたらエラーなくオブジェクトファイルが出来ました。

最終的に、>>770でいわれた通りの宣言で明示的実体化したら、
オブジェクトファイル内に実体化されたテンプレート関数が作成されていました。( nm -C で確認 )

何とかこの問題は乗りきれそうです。みなさんありがとうございました。
777デフォルトの名無しさん:2007/11/03(土) 20:53:38
流れ読まずに言うけどさ

>>775はC++をつかっているが、Cの範囲の質問したんだろ?
じゃあそれはCの質問でCスレいってこいやカスが
778デフォルトの名無しさん:2007/11/03(土) 21:01:53
自分の質問の内容がCの範疇であることも理解できず、従ってスレの使い分けができない、
そういうレベルの子のために

【初心者歓迎】C/C++室 Ver.44【環境依存OK】
http://pc11.2ch.net/test/read.cgi/tech/1194016813/l50

があるんだよ。
こっちは「C++」で、初心者と名の付く向こうが「C/C++」であり「環境依存OK」なのは伊達じゃない。
「問題を分離できないレベルの人はあっちへどうぞ」ということ。
779デフォルトの名無しさん:2007/11/03(土) 21:27:10
>>777
>>774を100回くらい声だして読んだら。
>>778
全部お前の勝手な匙加減じゃねーかw

C++はCの文法を含む。事実はこれだけ。
CスレでC++の質問をするのは無理があるが
C++スレで”Cにも”含まれる文法の質問をしたところで問題はない。
780デフォルトの名無しさん:2007/11/03(土) 21:32:00
まだやってんのかよ
781デフォルトの名無しさん:2007/11/03(土) 21:34:20
>>777みたいなアホが
勝手な自分ルールを押し付けてそれが一般化したら迷惑だからな。
言うことはきちんと言っておかんと。
782デフォルトの名無しさん:2007/11/03(土) 21:37:59
たまに自分の答えられない質問が出てくると
意味不明な論拠で必死にその質問にいちゃもんつけて排除しようとする回答者っているよな。
自分のプライドを傷つけられたと思うのかなんなのか。
783777:2007/11/03(土) 22:05:14
ごめんよ
俺が悪かったよ
だから議論おわってくらさい><
784デフォルトの名無しさん:2007/11/03(土) 22:06:50
だが断る
785デフォルトの名無しさん:2007/11/03(土) 22:52:42
>>782
まぁ、確かに「たまに」そういう回答者も現れるけど、
残りの大部分は馬鹿な質問者が逆ギレしてるだけのケースで、
今回も後者のパターンだよ。
786デフォルトの名無しさん:2007/11/03(土) 22:58:49
>>785
逆ギレの意味くらい理解してから使えよ。
787デフォルトの名無しさん:2007/11/04(日) 00:33:50
そうだな、回答者が一方的に発狂してるだけだもんな
788デフォルトの名無しさん:2007/11/04(日) 02:15:04
わざわざ利用者のほうでスレの使い分けしている意味を台無しにしようとがんばっている池沼がいるようなので記念カキコ
789デフォルトの名無しさん:2007/11/04(日) 02:57:31
能無し回答者(いや回答できないから正確には回答者じゃないや、自称回答者かw)が
頭の出来の悪さをズバリ指摘されて発狂しまくり、超ウケるwww
790デフォルトの名無しさん:2007/11/04(日) 03:01:34
もう触っちゃだめですよ。
791デフォルトの名無しさん:2007/11/04(日) 03:03:35
ageてる奴は同一人物
792デフォルトの名無しさん:2007/11/04(日) 03:10:44
問題ない派: 文法的観点 「strtok()はC++でも使えるでしょう><」
スレ違い派: 流儀的観点 「strtok()なんてC++では使いません><」
793デフォルトの名無しさん:2007/11/04(日) 03:16:32
もう触るなっての
794デフォルトの名無しさん:2007/11/04(日) 03:18:06
boost::stringtokでも使えww
795デフォルトの名無しさん:2007/11/04(日) 05:18:29
とりあえず777から794まであぼーんしますた
796デフォルトの名無しさん:2007/11/04(日) 05:57:12
そう、能無しのアホにとっては自分に都合の悪いレスはあぼーんするしかない
797デフォルトの名無しさん:2007/11/04(日) 06:26:11
>>792
いや使うだろ?
つうか使ってるんだが。
じゃあ何使うんだ?
普通に聞きたい。
798デフォルトの名無しさん:2007/11/04(日) 10:17:40
string で find_first_of() と substr() のループ、かな?
799デフォルトの名無しさん:2007/11/04(日) 10:24:13
strtokのほうが楽じゃん
800デフォルトの名無しさん:2007/11/04(日) 10:26:52
でも引数に副作用が出るのがキモイし、スレッド安全性とかも問題になることがあるだろう。
801デフォルトの名無しさん:2007/11/04(日) 10:27:08
つ boost::tokenizer
つ boost::spirit
つ std::stringstream
つ std::getline
802デフォルトの名無しさん:2007/11/04(日) 10:38:40
regexとxpressiveもな
803792:2007/11/04(日) 12:24:16
俺の場合は >>801-802 辺りで解決する。

まあ、俺が言いたかったのは、C++使いって
better C な使い方する人とか
Cっぽい書き方毛嫌いする人とか      (←俺はココ)
どっちの書き方もする雑食な人とか
色々いるよねってことなんだ。strtok()自体がどうこうじゃなくて。
804デフォルトの名無しさん:2007/11/04(日) 14:30:44
継承元の親クラスの引数付きのコンストラクタと同じ機能を子クラスにも実装したいとき、
子クラスでも同じようにコンストラクタを実装・宣言しなければいけませんか?

class BASE
{
  int num
public:
  BASE(int)
}

BASE::BASE(int a)
{
  num=a;
}


class SUB : public BASE
{
  int num; //←これを省略したい
public:
  SUB(int) //←これを省略したい
}

SUB::SUB(int b) //←これを省略したい
{
  num=b;
}
805デフォルトの名無しさん:2007/11/04(日) 14:45:37
そのソースだとコンパイル通らんだろ。

class SUB : public BASE
{
public:
  SUB(int);
}

SUB::SUB(int b)
 :BASE(b)
{
}

省略は無理。
806デフォルトの名無しさん:2007/11/04(日) 14:50:48
>>805
あれ?似たようなプログラムではなぜか通りました。ただし、親クラスの変数宣言の部分はprotected:に変えて、子クラスの変数宣言部は削除しました。。
>SUB::SUB(int b)
> :BASE(b)
こうすればよかったわけですね。
非常に助かりました。
ありがとうございましたm(_ _)m
807デフォルトの名無しさん:2007/11/04(日) 15:04:09
>>806
デフォルト引数を使って基底クラスのデフォルトコンストラクタ呼び出しにすれば
派生クラスの初期化リストから省略できる

class BASE
{
  int num;
public:
  BASE(int = 0);
};

BASE::BASE(int a)
{
  num=a;
}


class SUB : public BASE
{
public:

};
808デフォルトの名無しさん:2007/11/04(日) 15:09:35
>>807
ありがとうございます。
その場合、
SUB element(10); //numには10がセットされる
という初期化はできず、
SUB elemetnt; //numには0がセットされる
という使用方法のみになりますか?
809デフォルトの名無しさん:2007/11/04(日) 15:28:48
なるね
810デフォルトの名無しさん:2007/11/04(日) 16:02:17
>>809
了解です。
アドバイスありがとうございました.
811デフォルトの名無しさん:2007/11/04(日) 16:09:38
template<typename T>
void templateFunc(int a){}

template<typename T, typename U>
struct templateClass{
    templateClass(){
        struct D{
            T first;
            U second;
        };
        templateFunc<D>(0);
    }
};

void test(){
    templateClass<int, int> tc;
}

これがVC++2005ではコンパイル成功するんですけど
Fedora7付属のg++ 4.1.2だと

test.cpp: In constructor ‘templateClass<T, U>::templateClass() [with T = int, U = int]’:
test.cpp:17: instantiated from here
test.cpp:12: error: no matching function for call to ‘templateFunc(int)’

とエラーになってしまいます。struct Dを関数内じゃなくてtemplateClass内に移動すると、コンパイルは通ります。
これは何が間違ってるのでしょうか?
(g++4.2を試そうとしたんですがうまくインストールできませんでした。)
812デフォルトの名無しさん:2007/11/04(日) 16:22:35
14.3.1 Template type arguments

2 A type without linkage (3.5) shall not be used as a template-argument for a template type-parameter.
[ Example:
template <class T> class X { /* ... */ };
void f()
{
struct S { /* ... */ };
X<S> x3; // error: local type used as template-argument
X<S*> x4; // error: pointer to local type used as template-argument
}
-- end example ] [ Note: a template type argument may be an incomplete type (3.9). -- end note ]
813デフォルトの名無しさん:2007/11/04(日) 16:23:43
>>811
それはVC++2005が間違っています
関数スコープ内で定義されたクラスはテンプレートの引数としては使用できません

次の標準では可能になるように提案は出ていますが
いまはg++の挙動が正しいです
814811:2007/11/04(日) 16:27:45
>>812-813
あー、そうでしたか
g++のエラーメッセージもうちょっと分かりやすいと助かるんですけどねー
815デフォルトの名無しさん:2007/11/04(日) 16:42:48
>>813
横やり質問ですみませんが、具体的にコードのどの部分が文法違反でしょうか?
void test(){
templateClass<int, int> tc;
}
はOKじゃないんですか? 
816デフォルトの名無しさん:2007/11/04(日) 16:45:57
>templateFunc<D>(0); 

ここがだめ
ローカルな型をテンプレート引数に使おうとしている
817デフォルトの名無しさん:2007/11/04(日) 17:01:29
>>816
なるほど、リンケージを持たない型はダメってことですね

例えば

struct Widget { }; //構造体スコープにないのでローカルな型ではない

template<typename T, typename U>
struct templateClass{
templateClass(){
struct D{
T first;
U second;
};
templateFunc<Widget>(0); //変更
}
};

とかなら文法的にOKということですね。
818デフォルトの名無しさん:2007/11/04(日) 18:46:38
>>817
死ね役立たず。
人の足引っ張って楽しいかゴミクズ。
今すぐ死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。v死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。死ね。
819デフォルトの名無しさん:2007/11/04(日) 18:46:56
820デフォルトの名無しさん:2007/11/04(日) 18:58:00
??
821デフォルトの名無しさん:2007/11/04(日) 19:19:42
????
822デフォルトの名無しさん:2007/11/04(日) 19:22:26
????????
823デフォルトの名無しさん:2007/11/04(日) 19:22:57
????????????????
824デフォルトの名無しさん:2007/11/04(日) 19:23:38
????????????????????????????????
825デフォルトの名無しさん:2007/11/04(日) 19:34:48
????????????????????????????????????????????????????????????????
826デフォルトの名無しさん:2007/11/04(日) 19:52:24
化けてんじゃねーか ちゃんと文字コード意識汁!
827デフォルトの名無しさん:2007/11/04(日) 20:43:44
828デフォルトの名無しさん:2007/11/04(日) 20:53:41
>>818に隠されたメッセージを解読したぞ!
まずは「v死ね。」。これはVシネを表すと考えられる。
そして「ね。」。つまり「死がない」。
つまり!
>>818は、しがないVシネマニアなんだよ!なんだってー!おめがおめが!おめが!


だめだコレつまんねえな。一応書き込みしとくけど。
829デフォルトの名無しさん:2007/11/04(日) 21:21:51
>>828
あーあ、言っちゃった。
830デフォルトの名無しさん:2007/11/04(日) 22:42:51
流れぶった切って質問です。
クラス内クラスって、そのクラスの属するクラスへのアクセスってどうなるの?
privateにもアクセスできるのは正解?

VC8だとこんなのも通ったんだけど……

class test {
   std::string test_;
public:
   struct test2 {
      void operator()(test& value) {
         std::cout << value.test_ << std::endl;
      };
   };
public:
   test(std::string const& value) : test_(value) {};
};

int main() {
   test t("test");
   test::test2 t2;
   t2(t);
};
831デフォルトの名無しさん:2007/11/04(日) 22:45:28
>>830
どう考えても正解だろ
アクセス指定子ってクラス外部に対する指定なんだぜ?
832デフォルトの名無しさん:2007/11/04(日) 22:56:37
struct A
{
struct B { private: int i; };
struct C { int func(B& b) { return b.i; } };
};

クラス内クラス同士のアクセスってどうだったっけ?
このへん曖昧で、いつかちゃんと理解しとこうと思ってるんだけど。
833デフォルトの名無しさん:2007/11/04(日) 23:02:43
どうもこうも
プライベートとパブリックの考え方そのまんまだろ
現実と対して変わらん。
我が家のプライベートな所有物には俺も兄貴も弟もアクセスできる。
でも兄貴のプライベートを俺がアクセスすることはできない。
834デフォルトの名無しさん:2007/11/04(日) 23:06:08
フレンドシップの考え方とか
プライバシー・パブリシティの考え方とか
ちょっと欧米的だよな、クラスって
835デフォルトの名無しさん:2007/11/04(日) 23:10:03
1998 の規格では C++ 外側の private にはアクセスできなかったんだけど、
2003 の改定で内部クラスも「メンバ」であるってことでアクセスできるようになったんだぜ。
http://www.open-std.org/jtc1/sc22/wg21/docs/cwg_defects.html#45
836デフォルトの名無しさん:2007/11/04(日) 23:11:24
そーいやC++98とC++03の違いを良く知らないことに気が付いた。

まあいいか、C++09で全部覚えなおせば
837830:2007/11/04(日) 23:13:20
そうだったのか……ありがとう。
C++STD 9.7.1
The nested class is in the scope of its enclosing class.
つうことね。
838デフォルトの名無しさん:2007/11/04(日) 23:13:57
確かその辺、bcc5.5.1と5.6.4で挙動が違ったの覚えてる
839830:2007/11/04(日) 23:15:41
サンクス >835
1998とごっちゃになっていたのか……

>836
C++0x準拠の実装が出て来るの、いつになるのかね?
840デフォルトの名無しさん:2007/11/04(日) 23:18:43
>832
それはNGだと思う。
namespaceスコープと同じ挙動になるんじゃない?
841デフォルトの名無しさん:2007/11/04(日) 23:33:32
自分は14882:2003を持ってるけど

class E {
int x;
class B { };
class I {
B b; // error: E::B is private
int y;
void f(E* p, int i)
{
p->x = i; // error: E::x is private
}
};
int g(I* p)
{
return p->y; // error: I::y is private
}
};

こうなってる。つまり>>830はNG

見辛くてごめん
842835:2007/11/04(日) 23:54:13
>>841
あれ?

ごめん。 2003 の改定には間に合ってなかったみたい。
843デフォルトの名無しさん:2007/11/05(月) 00:11:35
>841
サンクス。11.8.1ですな。VC++8.0は間違いですな。
取り囲んでいるクラスにfriend追加しとくか。
844デフォルトの名無しさん:2007/11/05(月) 00:43:36
#include <iostream>
namespace hoge {
template<class T> struct base {
 template<class R>
 base& operator|(base<R>& r) {
  std::cout << "base::operator" << std::endl;
  return *this;
 }
};
struct tinko_type : base<tinko_type> {} tinko;
struct manko_type : base<manko_type> {} manko;
template<class L, class R>
base<L>& operator|(base<L>& l, base<R>& r) {
 std::cout << "hoge::operator |" << std::endl;
 return l;
}
}  // namespace hoge
template<class L, class R>
L& operator|(L& l, R& r) {
 std::cout << "::operator |" << std::endl;
 return l;
}
int main(int ac, char** av) {
 hoge::tinko | hoge::manko;
 return 0;
}
以上のプログラムのコンパイルには成功したのですが、実行結果に納得がいきません
漏れとしては hoge::base::operator| もしくは hoge::operator| が呼び出されると思ってたですよ
そしたら ::operator | が呼び出されてるですよ いったい禿はなにを考えてるですか?????
VC++2005EEとg++3.4.4(cygwin)で確認しました
845デフォルトの名無しさん:2007/11/05(月) 01:09:54
「BBS が止まっています」…(+ФyФ)?そうですか…
846デフォルトの名無しさん:2007/11/05(月) 01:21:55
>>844
厳密なルールは確認してないけど、派生クラスから基底クラスへの変換が要る
hoge::base::operator| や hoge::operator| よりも、まったく変換の要らない ::operator | が
優先されるのはそんなにおかしなことじゃないと思う。
847デフォルトの名無しさん:2007/11/05(月) 01:24:02
うろ覚えだが、たしか普通のLookupができなかった場合だけ、
Koenig Lookup、もといADLが行われるんじゃなかったかな。
しかも修飾してると働かないとかいうルールもあった気がする。
848デフォルトの名無しさん:2007/11/05(月) 02:17:34
void F( string & ){}

F( string( "test" ) ); // fail
string s( "test" );
F( s ); // OK
なぜ?
849デフォルトの名無しさん:2007/11/05(月) 02:20:53
コンパイルエラーくらい見ればいいのに。
850デフォルトの名無しさん:2007/11/05(月) 09:15:32
>>848
void F( string ){} か void F( const string & ){} にすれば大丈夫
851デフォルトの名無しさん:2007/11/05(月) 13:05:05
一時オブジェクトを非const参照には渡せない
852デフォルトの名無しさん:2007/11/05(月) 16:27:07
非const参照は左辺値で初期化しなければいけない
853デフォルトの名無しさん:2007/11/05(月) 20:39:07
>>849
これって、わかりにくいエラーメッセージが出てもおかしくない気がする。
でも、この程度でそんなことは免罪符にならないけどな。
854デフォルトの名無しさん:2007/11/05(月) 20:46:36
class C {
 explicit operator string() const;
};

このexplicit指定が許されるようになるらしい。
855デフォルトの名無しさん:2007/11/05(月) 22:27:02
(string)ってつけなきゃエラーか。
だったらtoStringでいいじゃねえか・・・
856デフォルトの名無しさん:2007/11/05(月) 22:33:54
>>855
テンプレート
857デフォルトの名無しさん:2007/11/06(火) 14:10:18
例えば、自作の文字列クラスを作る場合に、
mystr str1="abc";
mystr str2="def";
printmystr(str1+str2); // (str1+str2).print();とか実装するもの?
のような使い方をしたいと思います。
演算子のオーバーロードはこんな感じになると思うのですが、
mystr& operator+(mystr& lhs,mystr& rhs)
{
mystr* temp=new mystr;
temp.add(lhs);
temp.add(rhs);
return *temp;
}
この場合、newしたオブジェクトはどこかでdeleteされるんでしょうか?
858デフォルトの名無しさん:2007/11/06(火) 14:13:23
スミマセン。temp.add じゃなくて temp->add ですね。
859デフォルトの名無しさん:2007/11/06(火) 14:16:50
いいや、勝手にdeleteされたりはしない。自分でしなきゃだめ。

普通は
mystr operator+(const mystr& lhs,const mystr& rhs)
{
mystr temp;
temp.add(lhs);
temp.add(rhs);
return temp;
}
のようにする。
860857:2007/11/06(火) 14:26:37
>>859
それだと関数抜けた瞬間にtempのデストラクタが働いて、
呼び出し元で、
str3=str1+str2とか、
printmystr(str1+str2)とかができなくならないですか?
861デフォルトの名無しさん:2007/11/06(火) 14:42:56
mystr のコピーコンストラクタが正しく書かれていれば、ならない。
temp のデストラクタが動く前にコピーコンストラクタが起動して、operator+の呼び出し元にtempがコピーされる。
862857:2007/11/06(火) 14:53:05
>>861
あ、そういう風になってるんですね。
謎が解決しました。ありがとうございます。
863857:2007/11/06(火) 15:25:30
何度もスミマセン。
上記の場合だとstr1、str2にそれぞれ1万文字入っていたとして、
(1)str1からtempに1万文字コピー
(2)str2からtempの続きに1万文字コピー(計2万文字)
(3)コピーコンストラクタで呼び出し元に2万文字コピー
(4)tempがデストラクタで消える
となるので、
ポインタ渡しと比べて、(3)の分だけ一時メモリとコピーの時間がかかるんですよね?
864デフォルトの名無しさん:2007/11/06(火) 15:37:06
>>863
そこでRVOの登場というわけだ
865デフォルトの名無しさん:2007/11/06(火) 18:20:37
いやいや、ムーブセマンティクスの出番だ。まだだけど。
866デフォルトの名無しさん:2007/11/06(火) 18:29:16
return mystr(lhs.add(rhs));
とか出来るんだっけ?
867デフォルトの名無しさん:2007/11/06(火) 19:36:03
二項+の戻り値は参照にスンなボケ、といってたのは、
Effective C++だっけ?moreの方だっけ?
868デフォルトの名無しさん:2007/11/06(火) 21:13:23
無印Effectiveの方だね。

mystr str = str1 + str2 + st3 + str4;
なんかだとコピーコンストラクタの呼び出し(=全文字列のコピー)が何度も呼ばれることになる。

mystr str = str1;
str.add(str2);
str.add(str3);
str.add(str4);
の方が無駄なコピーが発生せずに同じ結果が得られる。

+で繋げるのは直感的でわかりやすいんだけど、
いっそのことoperator+等の二項演算子は実装しない方がいいかと。
869デフォルトの名無しさん:2007/11/06(火) 21:21:05
>>868
そう思うのはお前だけ
870デフォルトの名無しさん:2007/11/06(火) 21:33:37
>>868
つexpression template
871デフォルトの名無しさん:2007/11/06(火) 22:45:05
先ずは測定せよ。話はそれからだ。
872デフォルトの名無しさん:2007/11/06(火) 23:19:44
VC++EEなのですがstaticでconstなiとかjがないことされちゃいます>< (でもoperator<<には渡せる・・・

#include <string>
#include <iostream>

struct hoge {
 template<class T>
 hoge(const T) {}
};

struct hage {
};

static const int i = 1;

struct poge {
 static const int j = 2;

 static const hoge h1(i); // error C2061: 構文エラー : 識別子 'i'
 static const hoge h2(j); // error C2061: 構文エラー : 識別子 'j'
 static const hoge h3(hage());
};

int main(int ac, char** av) {
 std::cout << i << std::endl;
 std::cout << poge::j << std::endl;
 poge pooo;
 return 0;
}
873デフォルトの名無しさん:2007/11/06(火) 23:32:08
> static const hoge h1(i); // error C2061: 構文エラー : 識別子 'i' 
> static const hoge h2(j); // error C2061: 構文エラー : 識別子 'j' 
> static const hoge h3(hage()); 

これはいったいどういう動作を期待しているんだ? ちょっと説明してもらえまいか
874872:2007/11/06(火) 23:41:57
hogeのコンストラクタが引数の型をintとかhageとかで呼び出されることを期待しています
875デフォルトの名無しさん:2007/11/06(火) 23:44:23
>>872
> static const hoge h1(i); // error C2061: 構文エラー : 識別子 'i'
> static const hoge h2(j); // error C2061: 構文エラー : 識別子 'j'

これは多分 hoge 型の変数の宣言、定義を意図しているんだろうけど
コンパイラからは戻り値の型が const hoge で static なメンバ関数の
宣言に見えている

エラーメッセージにはそんなこと書いてなかった?
876872:2007/11/06(火) 23:53:17
あー なるほど
static const hoge h1(int(i));
static const hoge h1(int(j));
にしたらコンパイルできました
エラーメッセージはコメントのだけでした
ありがとうございます
877デフォルトの名無しさん:2007/11/07(水) 01:18:07
ディレクトリを作成する関数はありますか?
878デフォルトの名無しさん:2007/11/07(水) 01:20:19
APIにはあるがC++標準にはない。
879デフォルトの名無しさん:2007/11/07(水) 01:32:29
基底クラスBaseと派生クラスDerive1,Derive2,Derive3,...
があったとして派生クラスのポインタ(関数ポインタのように)を取得して

Base* ClassTable[] = {Derive1のポインタ,Derive2のポインタ,...};
Base* p = new ClassTable[0]();

というようなことをしたいのですが
もし可能ならどうしたらいいでしょうか
880デフォルトの名無しさん:2007/11/07(水) 01:37:49
関数ポインタでいいじゃん

Base *createDerive1() { return new Derive1(); }
Base *createDerive2() { return new Derive2(); }
...

Base *(*classTable[])() = { createDerive1, createDerive2, ... };
Base *p = classTable[0]();
881デフォルトの名無しさん:2007/11/07(水) 02:11:51
>>872-876
クラスの static メンバ変数宣言は、整数型に限って = で初期化子をつけることが
できるだけ。普通に初期化できる変数定義とは違う。クラス型を初期化することは
できなくて、当然コンストラクタも使えない。

>>875 メンバ関数の宣言ならカッコ内は型付の引数リストじゃないといけない。
そうじゃないからコンパイルエラーになってる。

>>876 その変更を加えると、 int(i) が int 型で仮引数名 i の引数になる(余計な
括弧は無視される)ので static なメンバ関数の宣言とみなされてコンパイルが通る。
h3 が最初からコンパイルできてるのもこの理由。
882デフォルトの名無しさん:2007/11/07(水) 02:13:58
それだと
派生クラスを追加するたびに
createDeriveXをつくり
classTableにそれを登録しないといけませんよね

追加する際の作業をなるべく減らしたかったのですが
構造体やクラス自身のポインタはやはり得られないようですね

例示いただいたものを踏まえつつ別の案を考えてみます
どうもありがとうございました
883デフォルトの名無しさん:2007/11/07(水) 02:25:38
>>879
なんか似たような話をこないだ見たような気がするが。

template<typename T>
Base* new_as_Base() { return new T; }

Base* (*(ClassTable[]))() = {&new_as_Base<Derived1>, &new_as_Base<Derived2>};
Base* p = ClassTable[1]();
884デフォルトの名無しさん:2007/11/07(水) 12:43:05
こういう時に、テンプレートって便利だな、と思う
885デフォルトの名無しさん:2007/11/07(水) 17:49:31
modern C++ designでもっと強力なのを見た気がする
886デフォルトの名無しさん:2007/11/07(水) 18:06:02
>>881
int(i) が int 型で仮引数名 i の引数になる

へぇーそうなんだ 知らなかった 文法エラーではないの?
887デフォルトの名無しさん:2007/11/07(水) 18:23:36
>(余計な括弧は無視される)
と書いてあるだろう
888デフォルトの名無しさん:2007/11/07(水) 18:26:10
>>887
それは規格でそうなっているの?
889デフォルトの名無しさん:2007/11/07(水) 18:26:55
>>887
キャストにも見えるんだけど、関数の仮引数のところでは無視されるってこと?
890デフォルトの名無しさん:2007/11/07(水) 18:27:49
>>887
余計な括弧が無視されたら inti になってしまうよ
891デフォルトの名無しさん:2007/11/07(水) 18:31:04
>>889
仮引数の括弧は無視されるみたい
Effective STLかな?の最も奇妙な解析で見た
メイヤーズ先生も知らなかったらしい
892デフォルトの名無しさん:2007/11/07(水) 18:32:54
>>890
return(0) は return0 にならないよね
893デフォルトの名無しさん:2007/11/07(水) 18:48:06
>>891
その本持ってるので見てみる まだ読んでないんだ

>>892
たしかに
ということは仮引数にint(i)とあった場合、括弧が無視された結果
は int i と解釈されるということだね
894デフォルトの名無しさん:2007/11/07(水) 18:52:32
BCCで確認した。勉強になりました。
895デフォルトの名無しさん:2007/11/07(水) 18:57:52
>>892
そりゃreturn(ってトークンがないからな
だから字句解析時にreturnと(ってなる
896デフォルトの名無しさん:2007/11/07(水) 19:14:36
     /ニYニヽ
    /( ゚ )( ゚ )ヽ
   /::::⌒`´⌒::::\   でっていうwwwwwwww
  | ,-)___(-、|
  | l   |-┬-|  l |
   \   `ー'´   /
897デフォルトの名無しさん:2007/11/08(木) 01:06:41
> Base* (*(ClassTable[]))() = {

これは、また・・・
898デフォルトの名無しさん:2007/11/08(木) 08:04:41
int i = 0;
int *pi = &i;

*pi; //これって式(expression??)?
899デフォルトの名無しさん:2007/11/08(木) 08:46:28
値が出てくるし、式じゃなかろうか
900デフォルトの名無しさん:2007/11/08(木) 09:19:54
セミコロンが付いてたら文だろう
901デフォルトの名無しさん:2007/11/08(木) 11:52:36
*pi が式。 *pi; が文。
902デフォルトの名無しさん:2007/11/08(木) 18:40:52
継承とstatic変数について質問です。

class Base {
static int x;
};

class C : public Base {}
class D : public Base {}

とすると、変数Base::xは派生したすべてのクラスから共通の実体が参照されます。

このとき、派生クラスごとに独立のstatic変数を与えたいのですが、
そのようなことを行う方法はありますでしょうか?
903デフォルトの名無しさん:2007/11/08(木) 18:56:32
>>902
派生クラスごとにstatic変数を定義する
904デフォルトの名無しさん:2007/11/08(木) 19:43:01
CRTP
905デフォルトの名無しさん:2007/11/08(木) 20:00:26
>>904
ありがとうございます。
テンプレートでクラスごとに実体化するのはなかなかよさそうだったので、これでいってみます。
906デフォルトの名無しさん:2007/11/08(木) 22:02:59
最近C++はじめたのだが。

あるオブジェクトをリスト管理しようとしてます。んで、そのオブジェクトは
別のオブジェクトが参照しているバッファ領域みたいなのを保持してる。
だから、そのバッファ領域のアドレスは変えたくない。

STLって、コピー前提のつくりだから、結局Cで使ってたリスト操作ライブラリ
引っ張ってきて使ってる。だっせえなあ、とか思いながら。

なんかいい方法ない?
907デフォルトの名無しさん:2007/11/08(木) 22:31:30
>>906
std::vectorならcapacityを超えない限りアドレス変更されない
std::listならそれぞれのオブジェクトのアドレスは変更されない
908デフォルトの名無しさん:2007/11/08(木) 22:34:17
オブジェクトを指すポインタをSTLコンテナに入れればいい。
もちろん、shared_ptrか何かを併用。
909デフォルトの名無しさん:2007/11/08(木) 22:43:03
LNK2001: 外部シンボル ""public: virtual void __thiscall CWnd::DoDataExchange(class CDataExchange *)" (?DoDataExchange@CWnd@@UAEXPAVCDataExchange@@@Z)" は未解決です。

Visual Studio 2005でMFCのアプリケーションをコンパイルすると
上のようなエラーがいっぱいでるのです。

これはどうやって回避すればいいのでしょうか?
910デフォルトの名無しさん:2007/11/08(木) 22:56:54
スレ違いだろ。Visual C++スレ行き
911デフォルトの名無しさん:2007/11/08(木) 22:57:27
912デフォルトの名無しさん:2007/11/08(木) 22:59:14
>>907
ウソウツ。
0x22ee94
0x22ee94
0x22ee94
0x4f0680
0x4f0690
0x4f06a0

void
insert()
{
  int i = 0;

  cout << &i << endl;
  mylist.push_back(i);
}

int
main()
{
  insert();
  insert();
  insert();

  list<int>::iterator itr;
  for (itr = mylist.begin(); itr != mylist.end(); itr++) {
    cout << &*itr << endl;
  }

  return 0;
}
913デフォルトの名無しさん:2007/11/08(木) 23:02:10
914デフォルトの名無しさん:2007/11/09(金) 00:42:42
>>912
、、、、なにしてんの? もしかして検証してるつもり?
915デフォルトの名無しさん:2007/11/09(金) 00:51:00
>>914
検証もクソも、STLのソースがメモリ確保して、コピーしてんだよ。
だから、auto変数を登録してもメモリ確保して、コピーされてんだよ。
チネ
916デフォルトの名無しさん:2007/11/09(金) 00:55:06
なにをとんちんかんな事を
917デフォルトの名無しさん:2007/11/09(金) 01:00:54
>>916

なんも知らないなら、ハジメカラソウイエヨ
918デフォルトの名無しさん:2007/11/09(金) 01:13:16
>>915
お前が何を検証したいのか良く分からん。
>だから、auto変数を登録してもメモリ確保して、コピーされてんだよ。
auto変数の登録って何だ?
mylist.push_back(i) は i の値をvectorに追加してるんだろう。
iの値を入れた器のアドレスと、i自身のアドレスが異なるのは当たり前だ。

もしかしてauto変数のアドレスを取得して登録でもしたいのか。
まさか、そんなことをしたいと考えるとは思えないが。
919デフォルトの名無しさん:2007/11/09(金) 01:14:22
補足。
「iの値を入れた器」はvector上でiの値を入れた器のこと。
920デフォルトの名無しさん:2007/11/09(金) 01:15:45
>>918
。。。。。。。。。。。。。。。。。

vectorに追加してるわけじゃないし、vectorだったら
n番目の要素のアドレスが、&myvector[n]と一致していることは、
保証されている。まずはそんくらいしっとけ、
921デフォルトの名無しさん:2007/11/09(金) 01:28:37
STLがcopy-in/copy-outであることと、内部バッファの拡充に伴う要素の移動とがごっちゃになってると思うんだ。

copy-in/copy-outであることが問題になるなら>>908のようにポインタでも格納しとけばいいと思う。

>>912で両者のアドレスが一致するようなことがあったら、それこそ病的な挙動だろ
922デフォルトの名無しさん:2007/11/09(金) 01:31:38
>>921
>>>912で両者のアドレスが一致するようなことがあったら、それこそ病的な挙動だろ

当たり前のことを理解できない、>>918がいるから説明してるわけで。
923デフォルトの名無しさん:2007/11/09(金) 01:33:39
本題とはそれたが、本題は

>std::listならそれぞれのオブジェクトのアドレスは変更されない

これが、ウソダッテコトダケダ
924デフォルトの名無しさん:2007/11/09(金) 01:40:16
>>923
「それぞれのオブジェクト」は「リスト内の要素」を指してたと思うんだ。
925デフォルトの名無しさん:2007/11/09(金) 01:42:45
ここは激しく議論のすれ違っているインターネッツですね

お互いに問題にしていることが違っているまま議論したら食い違って当たり前だろう
926デフォルトの名無しさん:2007/11/09(金) 01:43:09
>>918はlistとvectorを勘違いしてるけど、それ以外は妥当だろう。

>>923
>std::listならそれぞれのオブジェクトのアドレスは変更されない
の意味を勘違いしているだけのように見える。

>>921の後半にだけ反応しているけど、最初の2行はちゃんと読んだの?
927デフォルトの名無しさん:2007/11/09(金) 01:48:45
>>924
だから、リストに渡した要素をそのまま保持したりはしないんだって。
リストに渡した要素は、コピーが生成されてリストに保持される。

だからリスト内の要素のアドレスは、とうぜん渡したオブジェクトの
アドレスとは*異なる*。んで、本来は検証もクソもないんだわ。
ソースがそうなってるから。
928デフォルトの名無しさん:2007/11/09(金) 01:59:48
突っ込もうと思ったけどやめた
929デフォルトの名無しさん:2007/11/09(金) 02:04:19
>>928
いやいや、スマンw

>>921のいったことは理解した。アリガトウ。
930デフォルトの名無しさん:2007/11/09(金) 02:44:21
次スレは今建ってるやつで決まり?なんかテンプレがいろいろ抜けてるみたいだけど。
931デフォルトの名無しさん:2007/11/09(金) 07:56:16
>>924
おれもそう思う
listの場合追加、削除しても他の要素の反復子に影響はないから
932デフォルトの名無しさん:2007/11/09(金) 09:15:35
次スレいくらなんでも早すぎでしょう
なんらかの悪意があるんじゃないのか
933デフォルトの名無しさん:2007/11/09(金) 20:02:09
なあ、C++最近はじめたのだが、STLなどの標準ライブラリの
リファレンスってどこで見れるの?書籍でもWebでもよいのだけど。

「C++標準ライブラリチュートリアル&リファレンス (単行本) 」

がよさそうかなと思ったけど、絶版本で29,800円とかプレミアム
ついてるし。
934デフォルトの名無しさん:2007/11/09(金) 20:09:46
>>5のSGI-STLがおぬぬめ
935デフォルトの名無しさん:2007/11/09(金) 20:22:58
>>933
原著あるよ
936デフォルトの名無しさん:2007/11/09(金) 20:41:15
マクソのVisual Studio .NETタダ版を取ってくればSTLのマニュアルが見られる(英語)
937デフォルトの名無しさん:2007/11/09(金) 22:02:28
938デフォルトの名無しさん:2007/11/09(金) 22:42:32
MSDNライブラリをダウンロードしたりオンラインで見たりとか。
あとは検索性が難だが、JIS X 3014がJISCのWebサイトから見れる。
939デフォルトの名無しさん:2007/11/09(金) 22:56:01
なあ、下のクラスを-Wall -W -Weffc++でコンパイルすると、
なんかうるさい警告が山ほど出るけど、なんでだろ?

/usr/lib/gcc/i686-pc-cygwin/3.4.4/include/c++/bits/allocator.h:
  In instantiation of `std::allocator<MyClass*>':
/usr/lib/gcc/i686-pc-cygwin/3.4.4/include/c++/bits/stl_vector.h:79:
  instantiated from `std::_Vector_base<MyClass*, std::allocator<MyClass*> >::_Vector_impl'
/usr/lib/gcc/i686-pc-cygwin/3.4.4/include/c++/bits/stl_vector.h:110:
  instantiated from `std::_Vector_base<MyClass*, std::allocator<MyClass*> >'
/usr/lib/gcc/i686-pc-cygwin/3.4.4/include/c++/bits/stl_vector.h:142:
  instantiated from `std::vector<MyClass*, std::allocator<MyClass*> >'
main.cpp:52:
  instantiated from here

class MyClass {
  public:
    MyClass() {};
    virtual ~MyClass() {};
};
vector<MyClass*> myvec;

int
main()
{
  MyClass *p;

  p = new MyClass();
  myvec.push_back(p);
  return 0;
}
940デフォルトの名無しさん:2007/11/09(金) 23:18:00
スレチガイだったかもシレンが。。。

上記の警告を-Weffec++有効にしたままで抑制する方法ってあるんかな。
941デフォルトの名無しさん:2007/11/09(金) 23:37:02
よくわからないけど、STLはEffectiveC++スタイルでコーディングされていないってことなんじゃないの?
942912:2007/11/09(金) 23:53:17
>>915
>>907は確かに言葉が足りないと思うが、
安価先のレスを読めば意図を理解できるだろう。

それに比べて君は、君が馬鹿にしている>>906より言葉が足りない。
もう少し、人のいわんとすることを理解しようとする努力と、
人に伝えるための努力が必要だろう。 

まぁ、お前こそとっととチネがほんねだけれども。
943デフォルトの名無しさん:2007/11/10(土) 02:58:41
>>940
システムヘッダファイルからは警告を出さない、っていうオプションがあったような気がする
944デフォルトの名無しさん:2007/11/10(土) 10:24:53
>>943
システムヘッダから警告出さないのがデフォルトで、出せって言うオプションがある。

gcc がバグってたみたい。修正は、 4.2.x ?
http://gcc.gnu.org/bugzilla/show_bug.cgi?id=14172
945デフォルトの名無しさん:2007/11/10(土) 19:41:45
#include <iostream>

template< int N >
class class1
{
    public:
        void print()
        {
            std::cout<<"test"<<std::endl;
        }
};

template< int N >
class class2 :class1<N>
{
};

int main()
{
    class2<42> obj;
    obj.print(); //ここでコンパイルエラー
    return    0;
}

'class1<42>::print()' はアクセスできないとコンパイラに怒られます。
http://www.parashift.com/c++-faq-lite/templates.html#faq-35.19
と似たようなエラーであることは分かったので、
obj.class1<42>::print();とか
(class1<42>)(&obj)->print();とか試してみましたが、やはり怒られます。
どう解決すればよいのか教えていただければ幸いです。
946デフォルトの名無しさん:2007/11/10(土) 19:46:18
>>945
private継承だから?
947デフォルトの名無しさん:2007/11/10(土) 19:47:14
>>945
あなたが必要なのは
メンバ変数ですか?
それともテンプレートですか?
948デフォルトの名無しさん:2007/11/10(土) 19:53:45
>>946
すみません、そうでした。
しばらくjavaしかやってなかったものですっかりpublic継承忘れてました。

>>947
一応テンプレートです。
949デフォルトの名無しさん:2007/11/11(日) 23:50:02
void data_get(void** data);
こんなCの関数があって、これは俺が作ったものではないので変更できません。

typedef struct foo{
int a;
}foo;
こんな構造体があって、Cなら
foo *f;
data_get(&f);
こんな風に使います。

C++で今までVisual C++ 2005 で開発してこの関数を使うとき
foo* f;
data_get(reinterpret_cast<void**>(&f));
とやっていて、動作も特に問題が無かったのですが、g++4.1でコンパイルしたところ
warning: dereferencing type-punned pointer will break strict-aliasing rules
と怒られました。

一応この警告の意味とコードが標準に準拠してないことは理解したつもりですが
それでは、data_get関数をC++から安全に使うにはどのようにしたらいいでしょうか?

foo* f;
void** tmp = reinterpret_cast<void**>(&f);
data_get(tmp);
としてもも警告が出てしまいます。

void* tmp;
data_get(&tmp);
foo* f = reinterpret_cast<foo*>(tmp);
これだと警告が出ないのですが、大丈夫でしょうか。
950デフォルトの名無しさん:2007/11/11(日) 23:52:14
>>949
void* tmp; 
data_get(&tmp); 
foo* f = static_cast<foo*>(tmp); 

の方がいいんじゃない
951デフォルトの名無しさん:2007/11/11(日) 23:56:02
>>949
reinterpret_cast は良くないね。最後のやつを static_cast に変えるのが最善かな。
952デフォルトの名無しさん:2007/11/12(月) 00:02:30
>>949
C++なんだから、こっちで多重定義してしまえばいい。
inline foo_data_get(foo*& data)
{
void *p;
data_get(&p);
data = static_cast<foo*>(p);
}
953949:2007/11/12(月) 00:32:02
ありがとうございます、>>950>>952で行こうと思います。
ところで、void*からのキャストはreinterpret_castもstatic_castも同じだと思ってたんですが
違うんですか?
954デフォルトの名無しさん:2007/11/12(月) 00:33:34
>>953
reinterpret_cast は実装依存。 static_cast は foo* → void* への暗黙の変換の逆変換。
どっちも同じになる実装がほとんどだろうけどね。
955デフォルトの名無しさん:2007/11/12(月) 00:37:09
暗黙の変換を明示的に行うのがstatic_castだってeffective C++に書いてあった
956デフォルトの名無しさん:2007/11/12(月) 02:12:17
>>955
それだけではないけどね
void* -> T* の暗黙の変換はないけど
これもstatic_castの仕事の一つ
957デフォルトの名無しさん:2007/11/12(月) 08:10:10
test.cxxというファイル名だと、
__FILE__がtest.cxxになりますが、

#define test.cxx

と同等のことを__FILE__を使ってできませんか?
958デフォルトの名無しさん:2007/11/12(月) 08:48:00
>>957
識別氏にピリオドを含むことはできません。定義するマクロ名にマクロ展開の結果は使えません。
959デフォルトの名無しさん:2007/11/12(月) 22:55:33
>>949
g++ -fno-strict-aliasing じゃだめ?
960デフォルトの名無しさん:2007/11/13(火) 01:17:34
>>949
C++もCと同じだと思うけど、
汎用(void)のポインタへのポインタ型というのは規格上ないはず。
void func(void **);
int *p;
func((void **)&p);
こういうコードは移植性がなく動作は未定義。
正しくは、
void *vp = p;
f(&vp);
p = vp;

なので自分で書いてるとおりvoidポインタを介在させればよい。
foo *f;
void *tmp = f;
data_get(&tmp);
f = static_cast<foo*>(tmp);
でいいんでは?

961デフォルトの名無しさん:2007/11/13(火) 02:43:06
>>960
void**という型がないわけではない。
ただ、T**――Tはvoid以外の任意の型(あー、一応関数型も除く)――
とvoid**との間の変換が定義されていないだけ。
962デフォルトの名無しさん:2007/11/13(火) 03:39:21
グローバル変数の定義順序について質問させてください。

--- values.cpp ---
int values[] = { 5, 1, 2, 4, ... };

--- values.h ---
extern int values[];

--- table.cpp ---
#include "values.h"
int table[] = { values[0], values[1], values[2], ... };

こんな風に、異なる翻訳単位に2つのグローバル変数
values[] と table[] があって、table[] の初期化が values[] に
依存しているときに、コンパイラはこの依存関係(?)をちゃんと
検出してグローバル変数の定義順序を決めてくれるもんなんでしょうか?
詳しい方おられましたら、よろしくお願いします。
963デフォルトの名無しさん:2007/11/13(火) 03:44:08
定義した順に初期化される。
table.cppは int table[]... の前に extern int values[]; を展開する。
964962:2007/11/13(火) 03:44:24
すみません、このサンプルで御願いします…。

--- values.cpp ---
int values[] = { 5, 1, 2, 4, ... };
int get_value(int i) { return values[i]; }

--- values.h ---
int get_value(int);

--- table.cpp ---
#include "values.h"
int table[] = { get_values(0), get_values(1), get_value(2), ... };
965デフォルトの名無しさん:2007/11/13(火) 03:47:15
x定義した順に初期化される。
o宣言した順に
966デフォルトの名無しさん:2007/11/13(火) 03:47:57
自分でコンパイルしろよカス
967デフォルトの名無しさん:2007/11/13(火) 03:59:33
宣言した順ということは、どちらの翻訳単位が先に翻訳されるか
によって変わるということでしょうか。

手元のコンパイラ BorlandC++BuilderX でどちらも試してみましたが、
警告もエラーもなく期待通りに初期化されるようなので、良く分かりません。
table[] の初期化が values[] の初期化より先に行われるようなコンパイラが
あるとすれば、問題が起こるかもと思ったのですが。
968デフォルトの名無しさん:2007/11/13(火) 08:12:18
>>964
その場合 values は定数式で初期化されているので静的初期化になります。
table は定数式じゃないので動的初期化になります。非ローカルオブジェクトの
初期化は静的初期化が先で動的初期化が後なので、その例だと問題は起こり
ません。

静的初期化には特に順番というものがありません。動的初期化については
同じ翻訳単位内での順番は定義順と決まっていますが、翻訳単位をまたぐと
順番が定まらなくなりますので、その場合に問題が起こる可能性があります。
969949:2007/11/13(火) 08:20:18
>>959
それやったら負けかなと思ってる。
「最適化しても良い」って決まりですし。

>>960-961
ふむふむ、
そういえなvoid**はvoid*とは違って全然汎用ではないですね
970デフォルトの名無しさん:2007/11/13(火) 08:53:01
>>969
そりゃそうだ、void **はvoid *へのポインタに過ぎない。
971デフォルトの名無しさん:2007/11/13(火) 09:41:55
>>966
実行速度を計測するのと違って、自分の環境でたまたまうまくいけば
それで疑問が晴れる、というものではないから、それは見当違いの反応だよ。
972デフォルトの名無しさん:2007/11/13(火) 10:15:24
>>961
>>969
汎用(void)はおかしかった。void**がないわけではなく
”汎用として使えるポインタへのポインタ型はない”
と言いたかった。ここでいう汎用とはあるT型から
の変換とT型への変換ができるということ。
(不完全型へのポインタなので変換できない)

詳しくはCプログラミングFAQ
973デフォルトの名無しさん:2007/11/13(火) 10:25:43
教えてください。

void *vp;
があったとして
*vpのようにデリファレンスすることはできませんが
void** vpp;
があったとして、これを*vppのようにデリファレンスするのはOK
ですよね?(*vppはただのポインタで結果はvoid*となるので)

974973:2007/11/13(火) 10:27:03
訂正
(*vppはただのポインタで結果はvoid*となるので) ×
(vppはただのポインタで*vppの結果はvoid*となるので) ○


975973:2007/11/13(火) 10:40:19
念のため確認させて欲しいのですが

void MyMemoryAlloc(void **vpp, size_t n)
{
 .
 . 詳細は省略
 .

 *vpp = malloc(n * sizeof(T)); //確保したメモリへのポインタ

}

T *p;
void *vp = p;
MyMemoryAlloc(&vp, 10);
p = vp;

というのはOKですよね?というかよくありますよね?
976デフォルトの名無しさん:2007/11/13(火) 11:05:02
>>973
おk

だけど
>>975

T *p;
MyMemoryAlloc(&p, 10);

これでよくね?
ただし、TがPOD型のみ有効。
977デフォルトの名無しさん:2007/11/13(火) 11:26:56
is_podは現行のC++ではあまり使えないらしいし怖いのぅ
978973:2007/11/13(火) 11:45:20
>>976
ご説明ありがとうございます。

T *p;
MyMemoryAlloc(&p, 10);
としてしまうと、>>961さんご指摘のように
T** から void**への暗黙の変換が
できないですよね?
(POD型というのが分からなかったのですが。)
979デフォルトの名無しさん:2007/11/13(火) 14:44:25
>>968
ありがとうございます。勉強になりました。
>>962のサンプルの場合も、table[] の初期化子 (values[0] など)は
定数式ではない(配列の要素は const であっても定数式にならないん
でしたよね) ので、やはり values が table より先に(静的)初期化される、
と考えて良いんですね。
980デフォルトの名無しさん:2007/11/13(火) 15:22:00
>>978

あまり深く考えずに、

template<typename T> T * vp_assign( T * & lhs, void * rhs){
 return lhs = static_cast<T *>(rhs);
}

template<typename T> T * vpp_assign( T ** lhs, void ** rhs) {
 return vp_assign(*lhs, *rhs);
}

とか作って、それを使えばいいじゃまいか
981デフォルトの名無しさん:2007/11/14(水) 02:37:14
>>379
そうだよ。規格の 3.6.2 ね。
982981:2007/11/14(水) 02:37:59
盛大にアンカーミスった。 379 じゃなくて >>979 ね。
983デフォルトの名無しさん
>>975
p = vp はコンパイルできない。 static_cast が必要。

>>976
void** の引数に T** は渡せない。

>>980
意味が分からないから、たぶんやめたほうがいい。