09/03/20 09:58:48
std::sort で std::vector の要素をソートしようとしています。std::sort の第三引数にでたらめな比較結果を返す
比較関数を与えるとvector の要素の一部がおかしな値に置き換わってしまい、場合によってはプログラムが
異常終了してしまう現象に悩まされています。問題を再現するプログラムを用意しました。
#include <iostream>
#include <vector>
#include <algorithm>
#include <cassert>
int a[10] = {0, 0, 0, 1, 1, 1, 1, 0, 1, 1}, pos = 0;
class ComparisonFunc {
public: bool operator()(int i, int j) { return a[pos++] == 1; } };
void main() {
int t[] = {3, 5, 1, 4, 2}; std::vector<int> v(t, t+5);
std::sort(v.begin(), v.end(), ComparisonFunc()); assert(pos == 10);
for (std::vector<int>::iterator it = v.begin(); it != v.end(); ++it)
std::cout << *it << std::endl; }
このプログラムを実行すると第3要素の値がおかしくなります。VC++ 2008 Express Edition と
g++ 4.3.0 (MinGW) では一応実行が終了しますがIntel C コンパイラ 9.0 だと異常終了します。
環境は Windows XP SP3 (32ビット) です。「でたらめな比較結果を返す比較関数」を考えているのは、
ユーザが比較関数をスクリプト言語で定義できるシステムを作っているからです。operator() メソッドの
中でスクリプト言語で定義された比較関数を呼んで、その戻り値を operator() の戻り値として返す仕組みです。
そのためどんな比較関数が来てもプログラムが異常終了しないようにしたいと思います。どんな対策が
考えられるでしょうか? std::sort が比較関数の異常を検知して適当なところで処理を中断して例外でも
スローしてくれたらと思うのですがそこまで面倒は見てくれないようです。
128:デフォルトの名無しさん
09/03/20 10:47:27
>>127
std::sortに渡すコンパレータは辻褄のあった結果を返さないといけないと仕様で決められている。
そうでない場合の動作は未定義。
つまり、でたらめな結果を返す可能性のあるコンパレータはstd::sortには使えない。
ソート関数を自作するか、コンパレータを検証する関数を追加するしかないだろうね。
いずれにしても矛盾を検知しようと思ったら、O(n log n)では済まないと思う。
129:デフォルトの名無しさん
09/03/20 16:49:42
c++で作られたプログラムを逆アセンブルしてるんですが、アセンブリ言語について質問できるスレってありませんか?
130:デフォルトの名無しさん
09/03/20 17:16:32
このへんじゃね?
スレリンク(tech板)
131:デフォルトの名無しさん
09/03/20 17:20:20
C++で書かれたプログラムを逆アセ出来る人ってすごいなぁ。
意味不明じゃね?
132:デフォルトの名無しさん
09/03/20 17:30:16
逆アセするならそもそもアセンブラ理解しないと・・・。
80x86系統の命令コード表あると思うからそれ見ながら分解していけばいいかと
後単純なプログラムでコードがどうなるかをチェックし続けるっていうのが解析の基本><
133:デフォルトの名無しさん
09/03/20 17:34:18
>>130
ありがとうございました。
>>131
IDA pro とか簡単に逆アセンブルしてくれて、しかもグラフィカルに構造を表示してくれるので
あんまり知識が無くてもなんとなく分かります
しかも無料で使えるし。
ソフト自体が英語だしあんまり解説サイトとかが無いのが辛いですが・・。
134:131
09/03/20 19:47:12
IDA proってすげーー
135:デフォルトの名無しさん
09/03/20 19:56:39
引数オーバーロードによって戻り値を変えるプログラムが
g++ (1)3.3.6と(2)4.2.4で挙動が違います。
実行後 main戻り値が (1) => 2 / (2) => 1 となります。
NS1をNS2に書き換えると両方とも2が戻ります。
どっちの挙動が標準規格的には正しいですか?
//以下そのプログラム
#include <stdio.h>
namespace NS1 {
struct HUGA {};
}
namespace NS2 {
int get(...) { return 1; }
template <typename T>
int f() {
NS1::HUGA huga;
return get(&huga);
}
int get(NS1::HUGA * ) { return 2; }
}
int main() { return NS2::f<int>(); }
136:デフォルトの名無しさん
09/03/20 20:01:56
うーん。もしかして、Cのソースがあるものなら、直接アセンブラソース吐かせれば良いんじゃね?
バイナリを解析したいのならスマソ。
137:デフォルトの名無しさん
09/03/20 20:32:04
>>135
1
138:デフォルトの名無しさん
09/03/20 20:43:39
>>135
2
139:デフォルトの名無しさん
09/03/20 20:44:56
Visual C++2008では 2 になったけど
実際の動作は1にならないといけないみたいね。
vararg は言語によるすべての型チェックを無効にして
常にもっとも一致した型であることを強制するので
多重定義の解決では自動的に最優先になるみたい。
140:デフォルトの名無しさん
09/03/20 20:50:00
俺も気になってやってみた。
g++ (GCC) 3.4.5 (mingw special)では返り値は1で、
Borland C++ 5.5.1 for Win32では返り値は2だった。
…つまりg++ 4.2.4はちゃんと正しい進化を遂げているということか。
141:133
09/03/20 20:54:37
>>136
がっつりexeファイルです。
コマンドプロンプトで動く簡単(そう)なコンパイラがあるので、それを解析してデコンパイラを作ってみたくて・・。
にしても、2ちゃんねるのスレッド検索って、「アセンブラ」とか「アセンブリ」で検索すると結果が出るのに、
「アセンブ」で検索すると出ないんですね。ふしぎ!
142:デフォルトの名無しさん
09/03/20 21:02:36
(...)の絡む名前解決の定義ってISO/IEC 14882:2003にあるの?
もしなければ現段階では鼻から悪魔ってことになっちゃうんだけど
143:デフォルトの名無しさん
09/03/20 21:21:21
よこから質問なんですが
(...)
ってどうつかうんですか?
void func(int n, ...)
みたいのであればstdarg.hのマクロでやるのとは思うんですが
(...)みたいな...のみとはなんなんなんですか?
144:135
09/03/20 21:37:44
試してくれた人ありがとうございます。
>>139
...をvoid*にしても(2)はやっぱり1です。
ちなみにfの定義を非templateにすると両方とも
1になります。template関数が実体化されるときに
初めてオーバーロードの解決を行うっていう理屈で
あれば(1)が正しいような気もします。
ただそれはあまりにもマクロ的な発想だし(2)が
正しい?
NS1をNS2を書きかえると(2)が2に成るのも謎・・・。
145:デフォルトの名無しさん
09/03/20 23:05:11
URLリンク(page4.auctions.yahoo.co.jp)
146:デフォルトの名無しさん
09/03/21 00:58:20
>142
もちろんある。
っていうか、SFINAE を使う場合に用いられる場合がある。
>139
そして ... のオーバーロード解決の優先度は最低だ。
>常にもっとも一致した型であることを強制するので
これで優先されるのは関数テンプレートの時。
>144
> template関数が実体化されるときに
> 初めてオーバーロードの解決を行うっていう理屈で
> あれば(1)が正しいような気もします。
two phase lookup でぐぐれ。
dependent name の名前解決は実体化時まで遅延される。
nondependent name の名前解決は通常通り行われる。
get(&huga) は nondependent name なので名前解決は
通常通り行われ、この場合は get(...) に解決されるはず。
> 14882:2003
> 14.6 Name resolution/9
> If a name does not depend on a template-parameter (as defined in 14.6.2), a declaration (or set of declarations)
> for that name shall be in scope at the point where the name appears in the template definition; the
> name is bound to the declaration (or declarations) found at that point and this binding is not affected by
> declarations that are visible at the point of instantiation.
>
> 14.6.3 Non-dependent names/1
> Non-dependent names used in a template definition are
> found using the usual name lookup and bound at the
> point they are used.
147:デフォルトの名無しさん
09/03/21 01:07:07
補足。
>っていうか、SFINAE を使う場合に用いられる場合がある。
Modern C++ Design に優先順位が最低であることがポイントであるとした上で載ってるので
変態 templater にはそれなりに知られたテクニックだと思われ。
148:デフォルトの名無しさん
09/03/21 01:13:14
む・・・むずいw
149:135
09/03/21 01:20:21
>146
調べきれてないけど4.2.4の方が(規格的には)正しいような
気がしてきました。
NS2->NS1の書き換えはADLの関係でget(HUGA*)がヒット(2がかえる)。
だからget(HUGA*)を位置を変えずにNS1に持っていっても同様に
2がかえるのを確認しました。
get(void*)とget(HUGA*)をtemplate関数の特殊化とした場合
同様に2がかえる。
=> depend name?
それ以外の場合(オーバーロードの解決)は純粋に出現
順序で決定されると。
=> nondependent name?
もうちょっと調べてみます。ありがとうございます。
150:デフォルトの名無しさん
09/03/21 01:20:51
解決されるときに(...)の優先度が最低になるのが見付からないなぁ
ま事実だけ覚えときゃ十分か
151:デフォルトの名無しさん
09/03/21 01:48:31
>149
「NS2->NS1の書き換え」ってどこ書き換えたの?
テンプレート引数 T に依存するかどうかが dependent name かどうかの判断なので、
4.2.4 の挙動もおかしい気はする。
>それ以外の場合(オーバーロードの解決)は純粋に出現
>順序で決定されると。
先に宣言されたものが常に選ばれるみたいに読めて微妙。
>150
13.3.3.2/2
152:135
09/03/21 02:32:23
>151
> 「NS2->NS1の書き換え」ってどこ書き換えたの?
135のサンプルを「NS1->NS2の書き換え」の間違えです。
まとめると
//1を有効 & 他無効 => 2
//2を有効 & 他無効 => 1
//3を有効 & 他無効 => 2
#include <stdio.h>
namespace NS1 { struct HUGA {}; }
namespace NS2 {
int get(void*) { return 1; }
// int get(NS1::HUGA * ) { return 2; } //1
template <typename T>
int f() {
NS1::HUGA huga;
return get(&huga);
}
int get(NS1::HUGA * ) { return 2; } //2
}
namespace NS1 {
// int get(NS1::HUGA * ) { return 2; } //3
}
int main() { return NS2::f<int>(); }
153:135
09/03/21 02:42:13
補足
152のサンプルは3.3.6では全部2になります。
4.2.4みたいにADLの対象か否かで解決遅延対処になるか
否かってのはなんかしっくりこない・・・。
154:127
09/03/21 05:46:58
>>128
でたらめな比較結果を返す関数を与えた場合の動作は未定義なんですね。
致し方ないので既知の問題としてドキュメントに記載してユーザに注意
してもらうことにします。ありがとうございました。
155:デフォルトの名無しさん
09/03/21 08:00:42
比較関数全体をユーザ定義にするんじゃなくて、比較処理はC++で書いて、
条件を(比較結果がデタラメにならない程度に)カスタマイズできるように
すればいい気がするなぁ。
156:デフォルトの名無しさん
09/03/21 13:19:32
for_eachについて教えてほしいのですが、下記のコードでfor_eachの三番目の引数である
CPrint()に引数を設定ていないのにveciTableの要素が、void operator()(int iValue) ~へ渡されているのはどうしてですか?
#include <vector>
#include <algorithm>
#include <cstdio>
using namespace std;
struct CPrint {
void operator()(int iValue) { printf("%d\n", iValue); }
};
int main() {
vector<int> veciTable(3);
veciTable[0] = 111;
veciTable[1] = 222;
veciTable[2] = 333;
for_each(veciTable.begin(), veciTable.end(), CPrint());
return 0;
}
157:デフォルトの名無しさん
09/03/21 13:22:22
>>156
CPrint()(veciTable[0]) などのように operator () が呼び出されるから。
158:デフォルトの名無しさん
09/03/21 13:22:33
std::tr1::bindですが、↓がコンパイルできません。
Aのメンバ関数に引数を渡したいのではなくて、X::funcBにAを渡したいのです。
どうすればいいでしょうか。
class X {
class A { ... };
void funcA(void) { for_each(container.begin(), container.end(), std::tr1::bind(&X::funcB, _1)); }
void funcB(const A& a) { ... }
std::vector<A> container;
};
159:デフォルトの名無しさん
09/03/21 13:24:23
>>158
エラーメッセージは?
160:デフォルトの名無しさん
09/03/21 13:26:23
>>158
X のインスタンス指定が抜けてるよ。
std::tr1::bind(&X::funcB, this, _1) でいけるんじゃない?
161:158
09/03/21 13:46:42
>>160 であっさりうまくいきました!
昨日一晩の苦労が…。感激です。
>>159
thisがないときのエラーメッセージは(VC9ですが)
「error C2825: '_Fty': '::' が後に続くときは、クラスまたは名前空間でなければなりません」の後
「テンプレートのインスタンス化 'std::tr1::_Result_type1...' の参照を確認してください」という
bind特有の長いメッセージが続きます。
162:デフォルトの名無しさん
09/03/21 14:21:43
長文で申し訳ない。
>153
やっぱり 4.2.4 の挙動もおかしいと思う。
インスタンス化時点での名前解決の対象になるのは ADL のみみたいだけど、
そもそも、テンプレートパラメータに依存する dependent name に対するものだけなので。
ぴったりしたケースじゃないけど 4.3.1 に対してこんなバグレポもあがってるので、
gcc の挙動をそんなに信用できないと思う。
URLリンク(gcc.gnu.org)
テンプレートパラメータに依存しないものならインスタンス化を待たなくとも結果は変わらない
はずだし、遅延すると通常の名前に対するものと異なる直感に反する結果を与えかねないので、
定義時点で名前解決を行えばいい。
一方、テンプレートパラメータに依存する名前について定義時点のみで名前解決を行うとすると、
制約が強すぎる。例えば STL を使う場合、コンテナのヘッダをインクルードする前にコンテナの要素型と
必要な操作が宣言されていなければならない。
従って、インスタンス化まで名前の解決を遅延したいが何でもかんでも名前解決の対象にすると、
これまた直感に反する結果を与えかねない。
ということで、ADL のみに制限しているという理解。
……なんだが、14.6.4 の規定自体に問題がある気がしてきた。
ADL じゃない lookup はインスタンス化時点では行わないようにも読めるんだが、qualified name lookup も
インスタンス化時点で行われないと、dependent name な基本クラスのメンバにアクセスできなくなるので
そんなわけないと思うのだが。
C++ Templates The Complete Guide では dependent qualified name もインスタンス化時点で名前解決されるって
書いてあるんだが、一方、インスタンス化時点で名前解決されるのは ADL のみという記述も結構見かける。
163:デフォルトの名無しさん
09/03/21 14:27:34
g++の挙動はおかしいから
有名なソフトじゃ禁止コーディング規約いっぱいあるよ
C++のインプリで世界最悪なのがg++だし
164:デフォルトの名無しさん
09/03/21 20:10:57
アンチg++必死だなw
165:135
09/03/21 20:28:38
>162
つまみ食いみたいなレスになりますが・・・
>gcc の挙動をそんなに信用できないと思う。
私もgccのbugzilla幾つか確認したけどアサインされてないバグって
結構いっぱいありますな。外野があれこれいうのもなんだけどあれで
C++0x対応が収束するのやら。
> ということで、ADL のみに制限しているという理解。
そもそもオーバーロードは遅延名前解決の対象になるのか?
152の//3はnamespaceが違うのでget(void*)とはオーバーロードの
関係ではないわけで、そういう風に考えると、名前解決が遅延するのも
自然な気がしてきました(w
f()内でget呼び出しがTに依存していないのにも関わらず
名前解決が遅延するのがバグであったとしても、
本来はTに依存させて使用するのが普通で、そのバグを
前提にしたロジックを組まなければ何とかなるかと。
166:デフォルトの名無しさん
09/03/21 21:19:05
>165
> そもそもオーバーロードは遅延名前解決の対象になるのか?
> 152の//3はnamespaceが違うのでget(void*)とはオーバーロードの
> 関係ではないわけで、そういう風に考えると、名前解決が遅延するのも
> 自然な気がしてきました(w
名前解決(というより照合と呼ぶべきかもしれないが)とオーバーロードの解決は別のステップで、
まず名前の解決を行い、その後、名前解決によって発見された候補関数群から、呼び出すべき関数が
選び出される(これがオーバーロードの解決)。
なので、名前の解決が遅延された時点でオーバーロードの解決も遅延される。
ちなみに、private とかのアクセス制限が確認されるのはこの後。
167:デフォルトの名無しさん
09/03/22 01:01:10
>>163
>C++のインプリで世界最悪なのがg++だし
いるいる、「絶対○○」とか「世界一○○」とか何の根拠もなしに比較したかのように語る人w
168:デフォルトの名無しさん
09/03/22 01:28:11
ここの住人は頭がみんな良さそう
名前空間なんて、
松坂大輔
宮川大輔
のようなものとしか理解してないんだがな、俺的には。
169:デフォルトの名無しさん
09/03/22 02:52:53
よくわからんけど、gccは新しいのでやってくれ。windowsもlinuxも4.3.3以前のは入れてない。
170:デフォルトの名無しさん
09/03/22 13:12:11
gccについて疑問に感じたのなら、本家のforumが待ってるよ。
171:デフォルトの名無しさん
09/03/22 16:44:02
>>169
gccの4.x系は、Linux上での動作はいいが、Windows上での動作は問題があるって聞いてるんだが。
だからMinGWも最新安定版はg++は3.4.5なんだと。
(アルファ版なら4.x系もあるだろうが。)
172:デフォルトの名無しさん
09/03/22 16:46:44
gcc の話は↓こちらでどうぞ。
GCCについて part8
スレリンク(tech板)
173:デフォルトの名無しさん
09/03/23 12:22:42
聞いた話じゃなぁ
174:デフォルトの名無しさん
09/03/23 23:18:14
心を振るわせる話なら信用するのに
どうして鼓膜を振るわせる話は信用しようとしないのだ。
175:デフォルトの名無しさん
09/03/24 00:30:19
質問です
ソースファイルAでnewしたインスタンスを
別のソースファイルBでdeleteしたりしても大丈夫なんですか?
176:デフォルトの名無しさん
09/03/24 00:39:08
インスタンスの実体が対応してれば大丈夫だろ
177:デフォルトの名無しさん
09/03/24 01:03:40
変な設計だとは思うけどな
178:デフォルトの名無しさん
09/03/24 02:43:52
コンストラクタをcppに書いて、デストラクタをインラインでヘッダに書けば普通に起こる状況だな
179:デフォルトの名無しさん
09/03/24 08:21:36
クロスDLL問題ってのとは全くの別物だよね?
そもそもどうしてあれはダメなんだろ?
180:デフォルトの名無しさん
09/03/24 09:21:41
それは、それぞれでnewとdeleteの実装が別物だとうまくいかないという話。
msvcr90.dllですべて統一するとか、shared_ptrのようにdeleteごと渡すとかすればいい。
そして、コンパイラが違うとvtblやRTTIの形式が違うという話へ続く……。
181:デフォルトの名無しさん
09/03/24 09:28:56
そんな面倒事に悩まされる前に一つのモジュールに閉じ込める工夫に労力注げ…と
182:179
09/03/24 09:35:57
>>180-181
へーそういうことか。
ありがとう!
183:デフォルトの名無しさん
09/03/24 22:12:11
テンプレートの規則や仕様に
詳しくなれる本ってありますかね?
184:デフォルトの名無しさん
09/03/24 22:25:18
>>183
ない
185:デフォルトの名無しさん
09/03/24 22:26:32
>>184
嘘つくな洋書で一冊出てるだろ
教えろよ
186:デフォルトの名無しさん
09/03/24 22:27:32
>>185
詳しくなれるかどうかは別。
詳しく書いてるかもしれないけど。
187:デフォルトの名無しさん
09/03/24 22:29:14
c++ templatesとか
c++ template metaprogramming とか
188:デフォルトの名無しさん
09/03/24 22:30:10
URLリンク(books.google.com)
189:デフォルトの名無しさん
09/03/25 01:24:12
C++編(標準ライブラリ) 第27章 例外クラス
URLリンク(www.geocities.jp)
ここで紹介されている
std::overflow_error
std::underflow_error
が起こる例は、例えばどんなのがあるの?
前者はともかく後者がわからん。。。
190:デフォルトの名無しさん
09/03/25 03:14:14
標準じゃunderflow_error投げる規定は無さそうだな。 >189
191:189
09/03/25 09:38:25
>>190
そうなのか。
とりあえず作っちゃった謎の例外か?
どうも。
192:デフォルトの名無しさん
09/03/25 11:17:10
std::underflow_error - Google Code Search
URLリンク(www.google.com)
193:デフォルトの名無しさん
09/03/25 22:41:38
0をboolに変換するとfalse, 0でない数をboolに変換するとtrueになるんだよね?
これは分かる。
では
falseをintに変換すると0, trueをintに変換すると1
ってのは仕様上正しい?
特に後者が心配でならないんだが、標準で1になることが保証されている?
194:デフォルトの名無しさん
09/03/25 22:47:03
>>193
> 4.5 汎整数昇格
> 4 bool 型の右辺値は,int型の右辺値に変換することができる。falseは,0になり,trueは,1になる。
195:デフォルトの名無しさん
09/03/25 23:15:06
でも、int値をtrueと比較するのは危険なんだよね。
196:デフォルトの名無しさん
09/03/25 23:18:49
別に気にするな
引き継いで逃げ切ればOK
197:デフォルトの名無しさん
09/03/25 23:30:32
if ( int値を返す式 ) { }
は正常に動作するけど
if ( int値を返す式 == true ) {}
とやると意図したとおりに動かない可能性がでてくる
妙なルール。
198:デフォルトの名無しさん
09/03/26 17:19:01
>if ( int値を返す式 == true ) {}
は if ( int値を返す式 == 1 ) {} と同じ動作?
199:デフォルトの名無しさん
09/03/26 18:56:19
うん。
200:デフォルトの名無しさん
09/03/26 21:25:19
左辺をboolに変換して比較すれば問題ないのにな
変なルールだよな仕方ないけど
201:デフォルトの名無しさん
09/03/26 21:26:34
201
202:デフォルトの名無しさん
09/03/27 01:14:18
>>197
C が 0 以外は true と決めてたわけで better C としての
C++ は、従うしかなかったんちゃう?
まぁ、そんな言語は山ほどあるわけだが………
203:デフォルトの名無しさん
09/03/27 10:41:29
比較とか論理演算とかが結果を0と1で返すから
trueをそっちに合わせたんじゃね?
204:デフォルトの名無しさん
09/03/27 14:23:37
#define true 1
#define false 0
typedef char bool;
昔ありそうな超手抜き実装
205:デフォルトの名無しさん
09/03/27 14:24:25
手抜き?
206:デフォルトの名無しさん
09/03/27 14:30:14
Exceptional C++を読むとboolの必要性が説かれている
207:デフォルトの名無しさん
09/03/27 14:44:47
int値をbool値に変換するのは情報の欠落が生じるけど、その逆は生じない。
だからint型とbool型を比較すると、暗黙の型変換のルールに従って、bool型の方がint型に昇格する。
結果、>>198のようになって、意図したとおりに動かなくなる。仕様どおり!・3・
208:デフォルトの名無しさん
09/03/27 21:09:51
C++の副作用に関して良く解らないので教えてください。
int a=0;
int b=0;
int func(int c){ b=a; return c; }
このとき、
func(++a);
を通ると、bに1が入ることは保障されますよね?
func(a++);
この場合はどうでしょうか?
bに0が入る?
bに1が入る?
鼻から悪魔?
209:デフォルトの名無しさん
09/03/27 21:16:01
>>208
関数を呼ぶ直前と、関数から戻った直後に副作用完了点がある。
だから、どちらもbは1になる。
210:デフォルトの名無しさん
09/03/27 21:22:54
>>209
有難うございます。
211:デフォルトの名無しさん
09/03/27 21:28:25
>209
すいません。もうひとつ教えてください。
&& || ?: , 以外の演算子は副作用完了点ではないんですよね?
自分でオーバーロードした演算子の場合は
通常の関数と同じように関数に入る直前と戻った直後に副作用完了点はありますか?
212:デフォルトの名無しさん
09/03/27 21:32:31
>>211
ある。
ただし、最初にあげてる演算子をオーバーロードした場合、
組み込み演算子と違って、オペランドの評価順序が不定になったり、
ショートサーキットでなくなったりするのには注意。
213:デフォルトの名無しさん
09/03/27 21:42:28
有難うございます。
たびたびすみません。
「オペランドの評価順序が不定になる」とは何ですか?
組み込み演算子でも一般的に不定だと思うのですが、
オーバーロードによって不定でなかったものが不定になる場合があるのですか?
214:デフォルトの名無しさん
09/03/27 21:53:18
あ、
組み込みの && || ?: , 演算子の評価順序のことですね?
自己解決しました。
215:デフォルトの名無しさん
09/03/27 22:22:27
printfで64bit値(u_int64_t)を表示したい。
32bit環境では %llu
64bit環境では %lu
両対応でスマートな解決法ってないものだろうか?
define拾ってきて切り替えるくらいしか思いつかない
216:デフォルトの名無しさん
09/03/27 23:32:40
unsigned long long にキャストしていつでも %llu で表示する
217:デフォルトの名無しさん
09/03/27 23:35:15
VCとかは%I64uだったような
defineで切り替えるしかないんじゃね?
218:デフォルトの名無しさん
09/03/28 00:21:24
末尾にLがついてるのってlong int だよな?
219:デフォルトの名無しさん
09/03/28 00:25:57
>>216
その手があったか!
思考がループしてそこまで考え付かなかった。 thx
220:デフォルトの名無しさん
09/03/28 01:23:02
C99かC++0xでは<inttypes.h>のPRIu64を使う
221:デフォルトの名無しさん
09/03/28 19:28:24
>>220
それだと、uint64_t使えというところから始めないと。
222:193
09/03/28 19:54:02
>>194
あまりにもな遅レスすまんかった!!
ちょっと私用が。。。
汎整数昇格 了解しました。
ありがとう。
223:デフォルトの名無しさん
09/03/28 23:31:56
最近C++の勉強をはじめた者なんですが、n個のデータを打ち込んで
それらの平均値や標準偏差を求めるプログラムを打ち込んだところ、
.\例題2.1.cpp(10) : error C2679: 二項演算子 '>>' : 型 'const char [2]' の
右オペランドを扱う演算子が見つかりません (または変換できません)。
というエラーが出てしまったんですが、なにが原因かさっぱりわかりません。
いつもと同じように打ち込んだつもりなのですが、原因分かる方いませんか?
224:デフォルトの名無しさん
09/03/28 23:33:21
せめて例題2.1.cppの10行目くらい見せろよ
225:デフォルトの名無しさん
09/03/28 23:43:10
cout<<"nの値は?"; cin>>n>>"\n";
こうなっています。見たところどこにもミスはないと思うのですが・・・
226:デフォルトの名無しさん
09/03/28 23:45:32
>>225 cout<<"nの値は?"; cin>>n;
227:デフォルトの名無しさん
09/03/28 23:47:54
>>225
場合によって意味が変わるけど<<は出力、>>は入力
cin >>n
nに入力された値を入力
n>>"\n";
次に入力された値を"\n"に入力
だぞ?
おかしいだろ
228:デフォルトの名無しさん
09/03/28 23:50:52
>>226
ああ、なるほど!入力と出力の指令が混同してましたね(汗)
こりゃ動かんわ・・・どうもありがとうございました!!
229:デフォルトの名無しさん
09/03/29 00:00:58
以下のようなコードを見たのですが、
これってC++のルール上、
((T*)NULL)->function() は安全にコールできるんでしょうか?
class T {
void function(){
if (this == NULL){
return;
}
メンバにアクセス
}
}
function() が virtual だとしたらヌルポ例外ですよね?
230:デフォルトの名無しさん
09/03/29 00:06:01
>>299
C++にnull_pointer_exceptionなんて気の利いたもんはない。多分OSがそのプロセスを殺そうとするだけだろう。
経験則ではメンバに触れなければ落ちないけど規格で決まってる訳ではないだろうからお勧めしない。
231:デフォルトの名無しさん
09/03/29 00:07:05
誰もいないところにパスした。
>>230は>>229宛
232:デフォルトの名無しさん
09/03/29 00:13:00
>>229
((T*)NULL)-> が現れた時点で未定義動作になる。関数の中身は関係ない。
233:デフォルトの名無しさん
09/03/29 00:20:21
>>230 >>232
ありがとうございます。
234:デフォルトの名無しさん
09/03/29 00:41:21
((T*)NULL)->function()
このfunction()をstatic関数にしてみるとどうだろう?
有識者のご意見を聞きたい。
class T
{
public:
static void function(){}
};
int main()
{
((T*)NULL)->function();
return 0;
}
235:デフォルトの名無しさん
09/03/29 00:43:43
未定義。だいたいコンパイル通るのか
236:デフォルトの名無しさん
09/03/29 00:46:42
通るよ
237:234
09/03/29 00:49:17
ちゃんと質問する前にコンパイル済み。
通ったよ。g++ね。
C++では
(T*)NULL
自体は未定義じゃないよね?
>>232さんが言っているように
>((T*)NULL)-> が現れた時点で未定義動作になる。関数の中身は関係ない。
なのだとしたらstaticだろうが何だろうが確かに未定義になるのだろう。
が、static関数なら実質的にグローバル関数扱いなのではと思っているので疑問だった。
staticなメンバ関数はstaticなメンバ変数にしか触れることができないじゃん。
>>236
チェックしてくれてありがとう。
238:デフォルトの名無しさん
09/03/29 00:54:50
c++でcキャストは使うべきじゃないよ。 >229
239:デフォルトの名無しさん
09/03/29 00:55:55
今更そこに突っ込む不毛さ。
240:デフォルトの名無しさん
09/03/29 01:01:01
class Test
{
public:
void func( void ){ std::cout << "test"; }
};
int main( void )
{
static_cast<Test*>(NULL)->func();
return 0;
}
メンバ変数に触れなければこれもコンパイル通って動きそうだけど
さすがに未定義か?
241:デフォルトの名無しさん
09/03/29 01:04:39
>>240
括弧が足りなくないか?
242:デフォルトの名無しさん
09/03/29 01:06:19
ほぼ全ての環境で動くだろうけど未定義。
メンバ関数の呼び出しはつまるところ暗黙の引数thisを含む関数の呼び出しにすぎない。それがNULLであったとしても関数を実行するコードはあるので実行はされる。
でも未定義。
243:237
09/03/29 01:07:21
>>240
メンバ関数に触れていても通るよ。
コンパイラにはNULLかどうかなんてコンパイル時に分からない。
全く問題無く通り、実行時に鼻から悪魔が出て来ることとなる。
244:デフォルトの名無しさん
09/03/29 01:09:10
ところが
>>237
が言っているstatic関数になると話は別じゃね?
俺はstatic関数に詳しいとかいうわけじゃないから知らんけど、
グローバル関数に無理矢理クラス内というスコープつけたものという認識。
245:デフォルトの名無しさん
09/03/29 01:21:49
>>244
未定義動作になるのは、オブジェクトを指していない参照に対して単項 & や sizeof など特殊な
ものを除く演算子を適用した場合はいつでも。
アロー演算子 -> の右にあるのが何だとか関数が static だとかそんなのは関係ない。
246:244
09/03/29 01:27:35
>>245
へーそうなんだ、ありがと。
247:237
09/03/29 01:33:32
delete NULL;
ってのがあったな。めずらしく安全な例で。
248:デフォルトの名無しさん
09/03/29 01:41:17
>245
ポインタだからいいんじゃね?
4.10 Pointer conversions
(snip)
A null pointer constant can be converted to a pointer type;
the result is the null pointer value of that type and is distinguishable
from every other value of pointer to object or pointer to function type.
249:デフォルトの名無しさん
09/03/29 01:43:30
>>248
p->x は (*p).x と定義されている。
250:デフォルトの名無しさん
09/03/29 01:47:04
キャスト演算子だけなら問題ないってことだろ。
((T*)NULL);
251:デフォルトの名無しさん
09/03/29 02:09:54
std::vector<ポインタ型> v;
というのがあって
あるタイミングで
v.push_back(アドレス);
これやるとmemoty.stlの__rw_basis::data()で落ちるんです。どうやらタイミングとかが関係するみたいなんで
どなたかエスパーお願いできないでしょうか?再現ができなくて申し訳ないんですが・・・
252:デフォルトの名無しさん
09/03/29 02:13:33
>>251
スレ違いです。↓へどうぞ。
スレリンク(tech板)
253:デフォルトの名無しさん
09/03/29 02:16:08
環境書いてよ。それだけだとRogueWave製の標準ライブラリを使ってることぐらいしか分からない。
254:デフォルトの名無しさん
09/03/29 02:16:48
>>250
それはあたりまえ。だれもそんなところ問題にしていない。
255:デフォルトの名無しさん
09/03/29 10:59:55
__LINE__みたいに関数名表示するマクロありませんか?
256:デフォルトの名無しさん
09/03/29 11:02:31
標準ではC99で__func__。
コンパイラ拡張なら色々。
257:デフォルトの名無しさん
09/03/29 11:34:03
ちなみにマクロじゃないぜ。
258:デフォルトの名無しさん
09/03/29 17:40:26
戻り値が指定されてる関数で、
関数の最後にreturnが無くても
関数の最後まで到達しないなら
C++の規格上は正しくコンパイル、実行できることは保障されますか?
たとえば以下のような記述は問題ないですか?
int a(int n){
if (n){
return 0;
}
else {
return 1;
}
}
int b(int n){
if (n*n>=0){
return 0;
}
}
int c(int n){
while(1);
}
259:デフォルトの名無しさん
09/03/29 17:45:52
全部問題あります。
260:デフォルトの名無しさん
09/03/29 17:48:43
>>258
b()とc()は警告出るだろ
261:デフォルトの名無しさん
09/03/29 18:46:39
>>258
戻り値が指定されてる関数で、
関数の最後にreturnが無くても
関数の最後まで到達しないなら
C++の規格上は正しくコンパイル、実行できることは保障される。
ただ、b() はその条件を満たしていない。
262:デフォルトの名無しさん
09/03/29 19:44:12
nの値により条件を満たすのでは?
263:デフォルトの名無しさん
09/03/29 19:49:06
値によらないだろw
264:デフォルトの名無しさん
09/03/29 19:56:38
仮に
int b(int n){
if (n*n>=0){
return 0;
}
assert(false);
return 1;
}
と書いても鼻から悪魔が出るだけだな
# スレ違いっぽいが
265:デフォルトの名無しさん
09/03/29 21:15:29
俺は、例えばn=1000000って意味に取った
266:デフォルトの名無しさん
09/03/29 21:26:00
ああ二乗してるから必ず正なわけか
267:デフォルトの名無しさん
09/03/29 21:27:06
でもオーバーフローした時に悪魔だな
268:デフォルトの名無しさん
09/03/29 22:07:55
aもbもcも書いたとおりにコンパイルも動作もできるし
と思っているのだが,bはNGなのか?
269:デフォルトの名無しさん
09/03/29 22:12:18
bを実行したとき、nの二乗がintをoverflowしたときは鼻から悪魔が出る
それ以外はコンパイルも動作もOK
270:デフォルトの名無しさん
09/03/30 11:04:54
int b(int32_t n) {if (int64_t(n) * n >= 0) return 0;}
なら大丈夫かな?
271:デフォルトの名無しさん
09/03/30 12:38:17
大丈夫も大丈夫じゃないも、問題が起きそうな記述に警告を出してくれない方がよほど大丈夫じゃない
272:デフォルトの名無しさん
09/03/30 12:50:14
本当に簡単に鼻から悪魔るんだな
もうsqrt(abs(n)) <= INT_MAXとかoptionalとか使って部分関数として定義するしかないのか
273:デフォルトの名無しさん
09/03/30 20:07:59
コンマ演算子は副作用完了点で、
関数の引数のコンマは副作用完了点ではないのは理解してますが、
初期化子のコンマは副作用完了点でしょうか?
たとえば、以下のコードは正しく動きますか?
struct T {
int a,b;
......
};
int f();
void g(){
T t={ f(), t.a };
.......
}
void h(){
int a[2] = { f(), a[0] };
.......
}
274:デフォルトの名無しさん
09/03/30 20:27:52
あと、同じ型で複数の変数を定義する時のコンマは副作用完了点でしょうか?
たとえば、以下のコードは正しく動きますか?
void g(){
int a=f(),b=a;
......
}
275:デフォルトの名無しさん
09/03/30 22:21:29
継承した親クラスの実体を参照するメンバ変数を、なるべく無駄なメモリを消費せずに
実現したいのですが、よい方法はないでしょうか?
メンバ関数を使えばよいのは承知しているのですが、できれば "()" を書かずに済ませたいのです
struct coord { int x; int y; } ///< これを親にしたい
class state {
coord position; ///< この部分をメンバ変数として持つのではなく親から継承したい
coord velocity;
void foo();
}
extern void bar(coord& param);
void state::foo() { bar(position); bar(velocity); }
現在は親の参照を返すメソッドを作り、マクロでごまかして無理矢理実現しています
しかしマクロがソース全域に作用してしまうのでなんとかしたいのです
class state: public coord {
coord velocity;
coord& position() { return *this; } ///< 参照を追加
const coord& position() const { return *this; } ///< const 参照を追加
#define position position() ///< 強引にマクロ…関係ない部分まで作用してしまうのが難点
void foo(); ///< foo() 内で親の実体を *this ではなく position と書いてアクセスしたい!
}
試しにこんな風に書いてみたのですが、うまくいきませんでした
class state: public coord {
coord velocity;
const coord& position; /// こんな感じの参照をメモリ消費なしで定義したい
state(): position(*this) {} /// ここでエラー orz
void foo();
}
276:デフォルトの名無しさん
09/03/30 23:02:24
>>275
何かいろいろとアレな気がするが、少なくとも私の環境では
struct coord { int x; int y; };
class state: public coord {
coord velocity;
const coord& position;
state(): position(*this) {}
void foo();
};
というコードはコンパイルが通る。
エラーが出るというなら、コンパイラの名前とエラーメッセージを書いてほしい。
あと、クラス定義の最後のセミコロンを忘れていないかね?
277:デフォルトの名無しさん
09/03/30 23:11:06
セミコロンを忘れてしまい申し訳ないです。
コンパイラはVC++6.0 SP5+プロセッサパックでエラーメッセージは以下の通りです
error C2758: 'position' : オブジェクト コンストラクタの初期化リストで初期化されませんでした。
'position' の宣言を確認してください。
最近のコンパイラではこのソースでも動くとのことなので、こちらでもコンパイラを変えて
試してみようと思います。
278:デフォルトの名無しさん
09/03/30 23:12:07
>>275
なんか、やりたい動機がよくわからんのだが・・・。
stateからxは、継承関係にあるから当然そのまま参照できるよね。
void foo() { x = 1; }
親クラスのメンバであることが明示されたコードを書きたいってこと?
それなら
void foo() { coord::x = 1; }
これでいいと思うんだけど。
279:デフォルトの名無しさん
09/03/30 23:13:40
何度も書き込んで申し訳ありません、VC6でもコンパイルできました
warning C4355: 'this' : ベース メンバ初期化リストで使用されました。
エラーではなくワーニングが出ていたのが原因でした。お騒がせしました
280:デフォルトの名無しさん
09/03/30 23:15:01
>>278
foo()内部で bar(*this); ではなく bar(position) と書きたい、というのが動機です
281:デフォルトの名無しさん
09/03/30 23:25:21
>>280
あー、何となく気持ちはわかる。でも俺がやるとしたら
#define This (*this)
的な方法を選ぶかなぁ、実際にはやらないだろうけどww
282:デフォルトの名無しさん
09/03/31 00:17:31
ありがとうございます。説明不足で申し訳ないです。動機はもっと正確に書くと、
クラス同士が親子関係を持っていなかった時点と同じ可読性(できれば完全に同一の記述)を
クラス間に親子関係を持たせた後も維持したい、です
1. foo() 内部で bar((coord&)*this) や bar(position()) と書かずに以前のまま bar(position) と書きたい
2. foo()の外部で
state a;
coord b;
a = b;
a.position = b;
上記のように書いた場合に両者のコンストラクタを区別したい
区別のために ((coord&)a) = b と書きたくない
3. 親を参照するメンバ変数 position& が最適化後に実体を持たずに消えてほしい (調べてみたところ、VC6では消えませんでした)
マクロを使うことで制限つきながら上記3つは実現できたのですが
マクロの範囲が広すぎて関係ない部分まで影響が出るのが難点でした
要はほとんど好みの問題なのですが、どんな泥臭い方法でもいいので、
A. 無駄なメモリを消費しない自分自身(親の実体)への参照を定義するか、
B. プリプロセッサに頼らずにメンバ変数の記述でメンバ関数の呼び出しが行われるようにしたいのです
もしBが可能なのであれば、例えばコンストラクタがあってunion化できないメンバ変数へ
部分的なアクセスを行う擬似unionのようなことも(C++の理念的にどうなのかは別として)できそうです
283:デフォルトの名無しさん
09/03/31 00:20:18
マクロは全力で避けろ
継承は is a の関係
包含の方が多くの場合適切
なぜ男なんだ
284:デフォルトの名無しさん
09/03/31 00:41:45
>>282
なんか、説明聞いたらさらにツッコミたくなってしまったw
foo() の汎用性を持たせたいなら static foo(coord&) にして
メンバの場合
foo(*this);
変数の場合
coord c;
foo(c);
と俺はしたくなる。
ちなみに、bar((coord&)*this) は冗長なキャストだけど、わざとそう書いたんだよね・・・?
285:デフォルトの名無しさん
09/03/31 02:45:50
すみませんが、
>>273 >>274 お願いします。
286:デフォルトの名無しさん
09/03/31 02:58:04
>>285
少なくともVC++8で試してみたらコンパイルは通って動作も期待通りだった。
C++の言語仕様として保証されているものかどうかは知らん。
287:デフォルトの名無しさん
09/03/31 03:44:39
>>273
挙げられた例では未初期化のオブジェクトを参照しているので、
副作用完了点に関わらず、値が不定となる。つまり int i = i; と同じ。
ちなみに、初期化子および初期化宣言を区切るカンマではそれぞれで
「完全式」が区切られるので、副作用完了点となる。
ただし並べられたそれらの順番について C++ 2003 では規格に記述がなかったので、
次期改定で記述順に評価されることが決まる予定。
URLリンク(www.open-std.org)
なお、同じく次期改定で追加される initializer list については、・・・アレ、
評価順についての記述が見当たらない。大丈夫なんだろうか?
288:デフォルトの名無しさん
09/03/31 06:18:52
C++かCでデータ構造関係のアルゴリズムが詳細に
掲載されている本というとどんなのがありますかね?
289:デフォルトの名無しさん
09/03/31 21:09:06
>>287
ありがとうございます。
リンク先は非常に参考になりました。
すみませんが、依然 >>274 がわかりません。
おわかりでないでしょうか?
> 挙げられた例では未初期化のオブジェクトを参照しているので、
これに >>274 も含まれていたりしますか?
英語版wikipediaでは、
> At the end of an initializer; for example, after the evaluation of 5 in the declaration int a = 5;.
とありますが、
an initializer がどういう単位か分かりません。
MSDNでは、
> The end of a full initialization expression, such as the end of an initialization in a declaration statement.
とありますが、a full initialization expression が、
int a=5, b=a*10, *c=&a, &d=a;
のa,b,c,d それぞれなのか、この文全体なのかわかりません。
よろしくお願いします。
290:デフォルトの名無しさん
09/03/31 21:32:20
std::stack<std::string> s;
とした場合、
s.push(~)はsの中に~のコピーが出来る仕様でしょうか?
つまり
std::stack<std::string> s;
std::string *p=new std::string;
s.push(*p);
delete p;
としたとしても、スタックsは何の影響もなくs.top()とかしていいんでしょうか?
291:デフォルトの名無しさん
09/03/31 21:44:03
多分だめじゃよ、とーまんこー。
コンテナは値セマンティクスを要求するから
値として振舞わないものは入れられないのじゃ。
入れるならしぇあぽを入れなされ。
そして、そのプログラムは「依頼人のいない弁護士」を
保持することになる。
292:デフォルトの名無しさん
09/03/31 21:46:58
>>290
stackにpushした時点でstringがstack内にコピーされるから問題ない。
293:191
09/03/31 21:57:27
あぁ、ほんとだpushの引数に * が付いてた^^
すまんこ学園。つまり>>292が正解。
294:290
09/03/31 22:19:18
>>291-293
なるほど。
ありがとうございました。
これで安心して組めます。
295:デフォルトの名無しさん
09/03/31 22:30:08
すまんこ・・・
296:デフォルトの名無しさん
09/03/31 23:45:05
トライ木ってどんな木なのでしょうか?
データ構造がいまいちわかりません
297:デフォルトの名無しさん
09/04/01 00:09:25
>>296↓
URLリンク(ja.wikipedia.org)
298:デフォルトの名無しさん
09/04/01 00:12:16
たとえばABC,ADE,ABDの三要素のトライ木を書くとこんなかんじ
A-B-C
| |-D
|
|-D-E
左端のAが木のトップで右側が子要素な。
親から末端ノードまでの要素を連結すると登録した要素になる。
ツリーの深さはキー長に比例するけど1回辺りの比較が超軽いのが特徴。
これを改良したのにパトリシア木とかあるけど詳細は略
299:デフォルトの名無しさん
09/04/01 00:23:02
>>298
データ構造をどう表現していいの?
ノード毎にオブジェクト作るとかアホな
データ構造しか作れそうにないんだけど
意味あるのですかね?
300:デフォルトの名無しさん
09/04/01 00:42:58
N木使えばいいやん
301:デフォルトの名無しさん
09/04/01 00:47:31
ノード毎にオブジェクト作っていいんじゃないの。
302:デフォルトの名無しさん
09/04/01 01:19:15
そういや昔
map<string, map<string, map<string, map<string, string> > > >
みたいなの扱ったことあったなぁ、デバッグしててわけわかんなくなったりしたけどw
これもトライ木と言え・・・ないか。
303:デフォルトの名無しさん
09/04/01 01:21:12
>>302
発狂しそうだw
304:デフォルトの名無しさん
09/04/01 02:59:01
>>299
利点としては多数のキーが格納されてるときに、
一般的な二分木と比べてキーの探索が速いのと、メモリの無駄が少ない事
ただ、キーが文字列みたいに分解可能であることを要求するから
データの制約は2分木よりあるからトライ木って結構使いどころを選ぶんだよなー
305:デフォルトの名無しさん
09/04/01 03:10:28
トライと聞いてスクールウォーズを思い出した。
306:デフォルトの名無しさん
09/04/01 04:12:12
>>289
int a = 5;
↑この宣言において、 "initializer" (初期化子)は "= 5" の部分。
あとはわかるよね?
MSDN の "full initialization expression" は規格中に現れる用語では
ないのではっきりしないけど、おそらく上記の宣言における 5 に対応するもの
だろうと考えられる。
307:デフォルトの名無しさん
09/04/01 04:15:18
>>289
英語が読めるんなら規格のドラフトを読んだほうがいいかもね。
ただし「シーケンスポイント」というものは次期規格からはなくなってしまうようだ。
スレッド関連を規格化するための影響みたい。
"A finer-grained alternative to sequence points"
URLリンク(www.open-std.org)
308:デフォルトの名無しさん
09/04/01 08:10:13
>>306
わかりました。
有難うございます。
>>307
規格書は結構高かった気がするので....
そのうち手に入れます。
309:デフォルトの名無しさん
09/04/01 08:26:55
>>308
> 規格書は結構高かった気がするので....
いや、だからダウンロードできるドラフトを読めば、って話なんでしょ。
買うといってるのを止めるわけじゃないけど。
310:デフォルトの名無しさん
09/04/01 18:42:08
規格書いくらだっけ?7万くらいだっけ
昔興味本位で買おうとしたけどあまりにもバカ高くてやめた覚えがある
311:デフォルトの名無しさん
09/04/01 19:07:36
つーかJISの規格書って、なんでまたあんなに高価なの?
JISって営利目的の機関なの?
勝手に幻滅する俺がいる。
312:デフォルトの名無しさん
09/04/01 19:11:04
甘い汁をすすってる奴らがいるってことだろう
313:デフォルトの名無しさん
09/04/01 19:25:05
嫌なら買わなくてもいい
314:デフォルトの名無しさん
09/04/01 19:44:34
Cなどの規格はともかく、全国で数百冊しか売れない本ばかりだから内容もふくめて高いのは当然
315:デフォルトの名無しさん
09/04/01 21:03:22
俺は別にC++で生計立ててるわけじゃないから買わない。
俺も甘い汁をすする側になりたいものだ。
316:デフォルトの名無しさん
09/04/01 21:04:34
うんこした後にさ、ティッシュに血が付いてると、
この世の終わりみたいな気分になるよね。
JISの規格書が高いのもそのせい。
317:デフォルトの名無しさん
09/04/01 21:15:01
>>316
生々しいな
俺まだ血が付いてたことはないんだけど。。。
318:デフォルトの名無しさん
09/04/01 21:24:24
俺はもう慣れたけどな。
拭く前からわかるんだよね、硬さで。
319:デフォルトの名無しさん
09/04/01 22:02:25
いそいで拡張作業または増強作業にもどるんや
320:デフォルトの名無しさん
09/04/01 22:13:05
ツリーの圧縮って
どうゆうアルゴリズムあるのLZ法とか
今でも使うの?
321:デフォルトの名無しさん
09/04/01 22:27:56
"ツリーの圧縮"の検索結果 12 件中 1 - 12 件目 (0.22 秒)
>>320
流れから細部を省略しているのかもしれないけど
どれのことかわからん
322:デフォルトの名無しさん
09/04/01 22:42:35
>>319
それよりはラッパーを噛ませた方がいいぞ
穴が開いてしまうのはプログラマとしては許せんだろうが、これが実にいい
URLリンク(item.rakuten.co.jp)
323:デフォルトの名無しさん
09/04/01 22:57:11
>>322
うちの職場にいる!! そんな感じの使ってる人!!
俺の脳内ではワッシャと呼んでいる。
324:デフォルトの名無しさん
09/04/01 23:27:35
15くらいからケツ拭いたら必ず血がついてるわ
別に普通じゃね?
325:デフォルトの名無しさん
09/04/01 23:28:05
おまる?
326:デフォルトの名無しさん
09/04/01 23:30:14
いつのまにかG++相談室になってる
327:デフォルトの名無しさん
09/04/01 23:36:25
>>326
どういうこと?
(俺が空気読めなくて)意図を察せないんだが。
328:317
09/04/01 23:42:49
>>324
俺、今23だけど大丈夫なんだが・・・。
329:デフォルトの名無しさん
09/04/01 23:43:21
>>327
おまえにはがっかりだ
330:デフォルトの名無しさん
09/04/02 00:22:44
マクドの硬い椅子で膝組んだり色々涙ぐましい回避策取ってる女とか
ちょっとかわいそうに思うよ
G
331:デフォルトの名無しさん
09/04/02 01:04:39
トイレの水が赤く染まったときはさすがにやばいかもと思った
穴あきクッションって効くのかな?
332:デフォルトの名無しさん
09/04/02 01:14:48
>>331
脅すつもりはないが、あまりに量が多いようなら内臓由来の可能性もあるから
一度診てもらったほうがいいぞ。
333:デフォルトの名無しさん
09/04/02 01:18:06
>>310
さすがにそんなに高くない
JISは17,000円
ISOは380スイスフラン = 3万円くらい?
一応同じ内容の本をamazonから比較的安く購入することもできる
URLリンク(www.amazon.com)
18ドルで買えるPDFがどこかにあった気がするが忘れた
1998年の規格でよければ最終草案をタダで見れる
URLリンク(www.kuzbass.ru)
2003年の規格との差分はTC1としてまとめられてる
URLリンク(www.open-std.org)
G++な方々はボラギノール塗って整腸剤飲んで水分多めに取ると治りやすい
治らなかったら病院へ
334:デフォルトの名無しさん
09/04/02 01:27:56
甘い汁って、すするものなの?
335:デフォルトの名無しさん
09/04/02 01:32:35
URLリンク(www.google.co.jp)
URLリンク(www.google.co.jp)
336:デフォルトの名無しさん
09/04/02 02:17:54
>>334
慣用表現としてなら吸うものかな
337:デフォルトの名無しさん
09/04/02 02:37:13
下半身から滴る赤いしるをじゅるりスレ
338:デフォルトの名無しさん
09/04/02 02:38:29
案件でJava使ってサイトつくるよって言われて,
JBossとJSPとJava/CGIどれ選べば星界?
339:デフォルトの名無しさん
09/04/02 02:47:55
C++/CGIが正解
340:デフォルトの名無しさん
09/04/02 02:47:56
>>333
ドラフトなら 1998 年よりあとのやつは全部タダで見れるぜ。
URLリンク(www.open-std.org) から .pdf でダウンロードできる。
ちなみに今の最新は n2857 。
341:デフォルトの名無しさん
09/04/02 03:46:11
>>287
int i = i; は、値が不定じゃなくて未定義動作。
342:デフォルトの名無しさん
09/04/02 08:01:00
>>340
最新のは規格書の代替にならないんじゃ?
343:340
09/04/02 09:22:07
>>342
現行規格の代替なら 2003 年の直前のやつをダウンロードすればいい、
と思ったんだけど、あんまり古いのは無いみたいだった。 340 は嘘ね。ごめん。
ダウンロードできるいちばん古いのは 2004 年の N1577 だった。
途中で公開の方針が変わったのかな?
344:デフォルトの名無しさん
09/04/02 21:21:31
私はJISのサイトで2003年の規格の日本語訳が無料で読めるんでそれだけで十分ですが
英語の規格書を読みたい人ばっかなんですよね?
345:デフォルトの名無しさん
09/04/02 21:31:28
日本語でいいです。
346:デフォルトの名無しさん
09/04/02 21:38:59
検索できないし改頁潰れてるしときどき訳間違ってるし脚注抜けてるし
JISなんていりません
347:デフォルトの名無しさん
09/04/02 21:42:18
検索できないのは板杉だな
348:デフォルトの名無しさん
09/04/02 21:43:08
私検索できるPDFもってるけど。
349:デフォルトの名無しさん
09/04/02 21:52:04
>>348
それってダウンロードすると白く塗りつぶされるんでしょ。
350:デフォルトの名無しさん
09/04/02 21:58:02
>>349
うん。
でもクラック済み。
検索も印刷も普通にできるよ。
351:デフォルトの名無しさん
09/04/02 22:20:03
昔はクラックなんかせずとも正規購入できたのに
352:デフォルトの名無しさん
09/04/02 22:25:25
今のJISのサイトのは検索できるよ
ただし日本語とアラビア数字に限る。アルファベットは不可。何でこうなったんだろうね…
おれはJISのでもいいと思うけど、URLが決まらないのでこういうところで紹介するには不向きだと思う
テンプレに手順を書いてくれればいいんだけどね
353:デフォルトの名無しさん
09/04/02 22:25:26
実際に、ライブラリレベルじゃなくて、アプリKションレベルのものを書くとき、
mediatorパターンみたいな感じになっちゃって、
mediatorに相当するクラスのヘッダを、他のクラスから必ずincludeするような設計になっちゃったんだけど、
これって間違ってる?
C++の話題とはズレてごめんね>禿
354:デフォルトの名無しさん
09/04/02 22:30:52
検索できないってどういうこと?
私はLinux用のアクロバットリーダーのバージョン8を使っていますが検索機能付いてます。
JISの文書自体は文字単位で範囲選択できるので検索できない理由がわからないのですが?
355:デフォルトの名無しさん
09/04/02 22:33:35
JISのPDFは本文の文字の一部が画像になってる
356:デフォルトの名無しさん
09/04/02 22:46:44
どこですか?
357:デフォルトの名無しさん
09/04/02 22:48:12
いやいや、少し前のは全ページ画像だった。その代わりダウンロードしても見られたけど。
358:デフォルトの名無しさん
09/04/02 22:55:06
どういうこと?ってここで言われてもなぁ…JISに言ってくれよJISに
359:デフォルトの名無しさん
09/04/02 23:00:37
> ※最新バージョン9の使用は今しばらくお待ちください。
オマエ、ソレハナイダロウ
360:デフォルトの名無しさん
09/04/02 23:35:07
>>359
俺もそれ思ったwwww
えええええええ!?!?ってオモタ
361:デフォルトの名無しさん
09/04/02 23:53:54
今日は肛門疾患の話はないのか、寂しいな。
362:デフォルトの名無しさん
09/04/03 22:20:49
痔には乙痔湯!
喪前らも、服用しる
363:デフォルトの名無しさん
09/04/04 00:41:54
memchrと
strchrって何が違うの?
長さが既知だとすると性能一緒?
364:デフォルトの名無しさん
09/04/04 00:43:52
>>363
memchrの方が速いと思われ。
365:デフォルトの名無しさん
09/04/04 00:47:26
>>285
309 :動け動けウゴウゴ2ちゃんねる :09/03/30 23:16 ID:SGwSF7rQ
おねがいします。
【板名】 プログラム技術
【スレ名】C++相談室 part66
【スレのURL】スレリンク(tech板)
【名前欄】
【メール欄】
【本文】↓
すみませんが、
366:デフォルトの名無しさん
09/04/04 00:54:00
>>363
NULLで止まらないか止まるか
367:デフォルトの名無しさん
09/04/04 00:54:07
286 :動け動けウゴウゴ2ちゃんねる :09/03/30 20:26 ID:SGwSF7rQ
おねがいします。
【板名】 プログラム技術
【スレ名】C++相談室 part66
【スレのURL】スレリンク(tech板)
【名前欄】
【メール欄】
【本文】↓
あと、同じ型で複数の変数を定義する時のコンマは副作用完了点でしょうか?
たとえば、以下のコードは正しく動きますか?
368:デフォルトの名無しさん
09/04/04 00:58:31
>>366 '\0' と NULL をごっちゃにするな。
369:デフォルトの名無しさん
09/04/04 01:06:43
イヒヒ
370:デフォルトの名無しさん
09/04/04 01:11:04
null character
371:デフォルトの名無しさん
09/04/04 01:16:09
>>366
速度的にはどうなんですかね?
372:デフォルトの名無しさん
09/04/04 01:29:43
strchar 一文字単位で文字列終了文字判定
memchar カウンタがアップの判定だけ
どんなコードに落ちるかはCPUのアーキテクチャ次第
373:デフォルトの名無しさん
09/04/04 01:32:54
>>363
速度は実測が基本。
374:デフォルトの名無しさん
09/04/04 12:00:41
>>371
全く変わらない。
375:デフォルトの名無しさん
09/04/04 13:33:02
少なくともmemchrがstrchrより遅くなることはないから
出来る限りmemchrを使う
基本的にmem○○とstr○○は常にmem○○優先
376:デフォルトの名無しさん
09/04/04 13:39:43
いいえ。
377:デフォルトの名無しさん
09/04/04 13:48:56
memchrの方が2倍ぐらい遅いよ
378:デフォルトの名無しさん
09/04/04 14:04:58
>>377
根拠、或いは計測条件の提示を宜しく。
379:デフォルトの名無しさん
09/04/04 14:27:00
二倍なんてもんじゃないよ
380:デフォルトの名無しさん
09/04/04 17:16:31
FreeBSD 7.1-STABLE、Celeron 700MHz(i386)
で計測したらstrchrよりmemchrのほうが5パーセントほど
遅いという結果になりました。
どちらの関数もアセンブリ言語で書かれてあります。
381:デフォルトの名無しさん
09/04/04 19:10:53
std::string str="hoge";
const char * const p = str.c_str();
こういう使い方ってして良いの?
このケースではまあ最初からp="hoge"とすれば良いことになるけどもね。
382:デフォルトの名無しさん
09/04/04 19:13:10
c_strは使ってはいけない
383:デフォルトの名無しさん
09/04/04 19:13:33
>>382
str.c_str()がだめってこと?
どうして?
384:381
09/04/04 19:17:19
std::string str="hoge";
const char * const p = str.c_str();
str="piyopiyo";
const char * const q = str.c_str();
std::cout << reinterpret_cast<unsigned long>(p) << "\n" << reinterpret_cast<unsigned long>(q) << std::endl;
結果:pとqが違う値。
このようにstrが変わった時にpが無効になってる可能性はあるよね。
あるサンプルソースで似たようなコードがあって疑問だった。
385:デフォルトの名無しさん
09/04/04 19:17:31
>>382はバカ。
386:381
09/04/04 19:18:31
>>385
じゃあ気にしないようにするわ。
387:デフォルトの名無しさん
09/04/04 20:39:03
c_str() や data() が返すポンストコインタは
次に const でないメンバ関数が呼ばれるまでの間のみ有効という「時限式」なので
ポインタは保持しないほうがいいよっていうのが一般的な話。
わかってやるなら >>381 自体は違法じゃない。
388:381
09/04/04 20:40:56
>>387
分かりやすい説明ありがとう!
理解した。
389:デフォルトの名無しさん
09/04/05 01:03:50
std::string str("");
ってやってるヤツがいるんだが
std::stringはデフォルトコンストラクタでは空文字列にしてくれることが仕様上保証されているんだよね?
つまりstr("")は無駄だよね?
390:デフォルトの名無しさん
09/04/05 01:12:17
>>389
お前のようにデフォルトコンストラクタの仕様を知らないアホにも空文字列で初期化されることがわかるから無駄じゃない。
391:デフォルトの名無しさん
09/04/05 01:14:46
>>389
動作速度の点では無駄。
392:デフォルトの名無しさん
09/04/05 01:19:08
>>391
だよね。ありがと。
393:デフォルトの名無しさん
09/04/05 01:19:47
速度は実測が基本。
394:デフォルトの名無しさん
09/04/05 01:22:11
優秀なコンパイラで強い最適化オプションを指定していると、勝手にそれくらいは修正してくれないだろうか?
395:デフォルトの名無しさん
09/04/05 01:22:33
そもそも速度を気にするようなところでstd::stringを使うのが間違い。
動作速度でstr("")が無駄と言う奴は馬鹿。
396:デフォルトの名無しさん
09/04/05 01:23:24
>>395
お前も馬鹿。
397:デフォルトの名無しさん
09/04/05 01:24:10
コロッとだまされる>>392が一番馬鹿
398:デフォルトの名無しさん
09/04/05 01:26:00
>>394
優秀じゃなくてもふつうそれくらいするよ。
399:デフォルトの名無しさん
09/04/05 01:30:00
>>397
何がおかしいの?
具体的に言ってみ、お前の脳で言えるのなら。
400:デフォルトの名無しさん
09/04/05 01:33:20
>>399
str("")とデフォルトコンストラクタでは速度に差が無いから>>391はウソ。
以上。
401:デフォルトの名無しさん
09/04/05 01:35:56
もうお前ら全員安価つけてやれ、ホント、マジで頼むから。
402:デフォルトの名無しさん
09/04/05 01:37:19
5レス連続でアンカが付いている件について
403:デフォルトの名無しさん
09/04/05 01:38:58
>>402
いや、その前も含めて全部。
・・・と思ったら俺自身安価付けてなかった
ごめん吊ってくる。
404:デフォルトの名無しさん
09/04/05 01:42:10
>>400
残念ながら同じバイナリに落ち着かない以上、速度に差がないとはいえない。
出直しておいで坊や。
405:デフォルトの名無しさん
09/04/05 01:43:40
何か必死だな。
406:デフォルトの名無しさん
09/04/05 01:47:07
>>390が真理だな。
407:デフォルトの名無しさん
09/04/05 02:24:22
仲良くしなよ
408:デフォルトの名無しさん
09/04/05 02:30:49
文字列リテラルの使いまわしを認めないコンパイルオプションつけたらちょっとバイナリが増える・・・・・かな?
409:デフォルトの名無しさん
09/04/05 02:55:07
>>404
同じ()バイナリ()落ち着く()
スイーツ()ですか
410:デフォルトの名無しさん
09/04/05 02:57:50
結論
str("")は無駄ではない。
411:デフォルトの名無しさん
09/04/05 02:58:05
ねーよ
412:デフォルトの名無しさん
09/04/05 03:01:33
std::stringはデフォルトコンストラクタでは空文字列にしてくれることが仕様上保証されているんだよね?
なんて醜態晒すくらいなら
std::string str("");
と書く方がよほどスマート。
413:デフォルトの名無しさん
09/04/05 04:02:57
次期規格ではstring()はstring("")に委譲する実装になるだろうから
そうなれば本当に速度に差はなくなるだろう
今は知らん
414:デフォルトの名無しさん
09/04/05 04:48:42
普通に、こう考えろ
char* str = NULL;
char* str = "";
同じか?w
415:デフォルトの名無しさん
09/04/05 07:26:06
全角のアルファベットを打つ奴はゆとり
416:デフォルトの名無しさん
09/04/05 07:47:48
全角ってなんですか?
417:デフォルトの名無しさん
09/04/05 08:47:43
>>353
> mediatorに相当するクラスのヘッダ
の中では前方宣言するのが吉。
そうしないと冗長すぎる依存関係になってしまう。
アプリケーション全体が10kくらいなら気にしないのも有りかも。
418:デフォルトの名無しさん
09/04/05 09:12:22
C言語でWEB操作したいです
証券会社にログインして株価を監視して自動売買が目標です
まずはC言語でWEBページを開く方法を教えてください
419:デフォルトの名無しさん
09/04/05 09:58:03
>>413
> 次期規格ではstring()はstring("")に委譲する実装になるだろうから
なんでそんなとこ変わるの?
420:デフォルトの名無しさん
09/04/05 10:40:31
>>418
WebProg板へどうぞ。
421:デフォルトの名無しさん
09/04/05 13:12:14
>>418
C Web Download をgoogle検索
あきらめろ
422:デフォルトの名無しさん
09/04/05 13:32:16
>>418
スレリンク(tech板)
423:デフォルトの名無しさん
09/04/05 18:03:11
デストラクタはpublicで宣言するものだよね?
privateで宣言すると、
まあ普通にコンパイルエラーになるんだけど、
特殊な状況でprivateなデストラクタってある?
なんか俺の知らないイディオムでありそうな気がしてきたんだが。
424:デフォルトの名無しさん
09/04/05 18:16:00
deleteをオーバーロードしてるとかじゃないとコンパイルすら通らなくね?
425:423
09/04/05 18:18:06
>>424
そう、通らない。
でも例によってC++は深遠だからさ、
俺が知らないだけで便利なイディオムがあったりするかな~って興味が出てきた。
426:デフォルトの名無しさん
09/04/05 18:21:59
とりあえずnewで生成してみろよ
427:デフォルトの名無しさん
09/04/05 18:22:20
自動変数や静的変数としては使えないが、newすることは出来る。
deleteはクラスのメンバ関数から出来る。
だから、使えないことはない。具体的にどう役立つのかは分からんが。
428:423
09/04/05 18:25:28
あ~、newで作るのか。
なるほどね。
429:デフォルトの名無しさん
09/04/05 18:26:30
Effective C++にて
const char* const authorName="ScottMeyers";//方式1
const std::string authorName="ScottMeyers";//方式2
この2つが紹介されていたんだけど、結局どっちが良いの?
本によれば方式2の方が良いよ的な書き方されていたんだけど、どうして方式2が良いのか分からない。
430:デフォルトの名無しさん
09/04/05 18:35:41
class MyClass{};
として、
boost::shared_ptr<MyClass> p(new MyClass);
だと大丈夫なのに
boost::shared_ptr<MyClass> p=new MyClass;
だとダメなのは何故でしょうか?
私は宣言時に
(初期化値)とするのと
=初期化値とするのは
等価にコンストラクタを呼び出す物だと思っていたので驚きました。
431:デフォルトの名無しさん
09/04/05 18:38:14
>>430
boost::shared_ptr<MyClass> p=boost::shared_ptr<MyClass>(new MyClass);
432:デフォルトの名無しさん
09/04/05 18:41:49
>>430
コンストラクタに explicit がついていると
> boost::shared_ptr<MyClass> p=new MyClass;
は不可能になる。
例えば
class MyClassA {
MyClassA(int n);
};
class MyClassB {
explicit MyClassB(int n);
};
となっていた場合、
MyClassA a(3); // OK
MyClassA a = 3; // OK
MyClassB b(3); // OK
MyClassB b = 3; // NG
となる。
また、
void myFuncA(MyClassA a);
void myFuncB(MyClassB b);
という関数があった場合
myFuncA(3); // OK
myFuncB(3); // NG
となる。myFuncB(MyClassB(3)) は可能。
433:デフォルトの名無しさん
09/04/05 18:42:16
>>431
それはキャストですよね。
つまりキャストしないとダメなんでしょうか?
なぜですか?
…あ、もしかして
boost::shared_ptr<MyClass>のコンストラクタが
explicitになっているということでしょうか?
434:433
09/04/05 18:43:20
>>432
すみません。
再読込してませんでした(> <)
失礼致しました。
explicitですね。
もうちょっと勉強して出直してきます。
435:デフォルトの名無しさん
09/04/05 18:44:05
>>430
スレリンク(tech板:106-109番)
436:432
09/04/05 18:44:11
ごめん、>>432の例だとコンストラクタがprivateになってるね。public: を付け足して読んでほしい。
437:433
09/04/05 18:51:15
>>435-436
ありがとうございます。
>newしたらすぐにスマートポインタにセットさせるのが基本。
これがRAIIってやつでしょうか?
438:デフォルトの名無しさん
09/04/05 18:52:46
>>423
カスタムデリータを使うときにデストラクタをprivateにして隠して、カスタムデリータ外から勝手に呼べなくする。
439:423
09/04/05 19:03:36
>>438
あーなるほどね。
やっぱあるんだ。
サンクス
440:デフォルトの名無しさん
09/04/05 21:04:47
仮想関数として指定するキーワードvirtualは、どれだけ付けるのが正しい?
例えば
class Base
{
public:
virtual void m_func(){std::cout << "Base m_func!" << std::endl;};
Base(){std::cout << "Base Constructor!" << std::endl;};
virtual ~Base(){std::cout << "Base Destructor!" << std::endl;};
};
class Derived : public Base
{
public:
void m_func(){std::cout << "Derived m_func!" << std::endl;};
Derived(){std::cout << "Derived Constructor!" << std::endl;};
virtual ~Derived(){std::cout << "Derived Destructor!" << std::endl;};
};
class Derived_Derived : public Derived
{
public:
void m_func(){std::cout << "Derived_Derived m_func!" << std::endl;};
Derived_Derived(){std::cout << "Derived_Derived Constructor!" << std::endl;};
virtual ~Derived_Derived(){std::cout << "Derived_Derived Destructor!" << std::endl;};
};
441:440
09/04/05 21:06:11
んで呼び出す時は
void foo()
{
Base* p=new Derived;
Base* q=new Derived_Derived;
Derived* r=new Derived_Derived;
p->m_func();
q->m_func();
r->m_func();
delete p;
delete q;
delete r;
}
このように、俺はBaseのm_func()にしかキーワードvirtualを付けていないんだが、これであってる?
スレリンク(win板:127番)
442:440
09/04/05 21:09:30
ごめん
別スレで無礼者がいたから
そいつへレスしようとしてたら
間違ってこっちにリンク張っちまった。>>441
マジごめん。
443:デフォルトの名無しさん
09/04/05 21:17:07
virtualつけたメンバ関数は、派生クラスではvirtualをつけてようがつけてまいが関係なく
仮想関数になる
DerivedもDerived_Derivedもvirtualはつけてもつけなくても一緒
444:デフォルトの名無しさん
09/04/05 21:50:28
>>443
ありがとう。
ちなみにどちらでも同じということだが、その場合
virtualは付ける方が良いとか付けない方が良いとかそういう慣習があったりする?
445:デフォルトの名無しさん
09/04/05 21:54:58
>>440のコードを
Baseでvirtualを付けておき、DerivedとDerived_Derivedではvirtual付けない版と、
Baseでvirtualを付けておき、DerivedとDerived_Derivedでもvirtual付ける版と
両方を作ってビルドしてみた。
g++ -O2 ~~.cpp
としたのだが、挙動は一緒みたいだが、バイナリは違うものになった。
何故?
446:デフォルトの名無しさん
09/04/05 22:09:48
-Sで試して確かめるならまだしも…
447:デフォルトの名無しさん
09/04/05 22:24:44
>>446
-Sだったら同じバイナリになったわ。
なんで??
448:447
09/04/05 22:25:58
>同じバイナリ
→アセンブラコード
449:デフォルトの名無しさん
09/04/06 00:14:09
>>444
C++ Coding Standards では派生クラスでもつけたほうがよいと書いてある。
(38項.安全なオーバーライドを身につけよう)
単に利用者に意図を明確にするためだけどね。
450:デフォルトの名無しさん
09/04/06 00:15:07
速度限界まで最適化するときに
virtualってどう扱うべきなのですかね?
451:デフォルトの名無しさん
09/04/06 00:26:22
@Override みたいなのが欲しいよね
452:デフォルトの名無しさん
09/04/06 00:41:43
そこで属性でしょきっと。
453:デフォルトの名無しさん
09/04/06 00:43:53
#define override virtualってうちの会社の元Delphi使いな先輩がやってた。
454:デフォルトの名無しさん
09/04/06 00:53:48
>423
遅レスだけど、削除を別のfriend classに委譲する時なんかで使う。
こんなの
class A {
private:
^A() {};
class deleter {
void operator()(A* target) { delete target; };
}
friend deleter;
public:
boost::shared_ptr<A> creator() { return boost::shared_ptr<A>(new A, deleter()); };
}
455:デフォルトの名無しさん
09/04/06 17:32:53
class Singleton {
Singleton() {}
~Singleton() {}
public:
static Singleton& Instance() {
static Singleton instance;
return instance;
}
};
みたいなやり方がどっかに載って無かったかな。
456:423
09/04/06 21:40:38
>>454-455
あるのね。
うーん、やっぱ奥が深い。
457:デフォルトの名無しさん
09/04/07 11:04:11
関係ないけど
singletonをtempleteにするとctorはpublicにせざるをえないのかな?
よくそういう実装をみかけるけど、新しいインスタンスを作れるのがイヤなのですが
458:デフォルトの名無しさん
09/04/07 11:20:52
ctorをprivateにしてsingletonをfriendにすればええがな
459:デフォルトの名無しさん
09/04/07 11:22:59
そもそもシングルトンをテンプレートにしてまで量産しようという考え自体が間違いだな。
460:デフォルトの名無しさん
09/04/07 19:15:55
CamelCaseにするかcamelCaseにするかcamel_case(underscore_style)にするか、
その基準とか主張とかメリットとかデメリットを知りたいんだが、
みんなどうしてる?
確かBoostは俺の知る限りunderscore_styleだったと思うのだが。
461:デフォルトの名無しさん
09/04/07 19:27:32
>>459
量産するなんて誰か言ったの?
462:デフォルトの名無しさん
09/04/07 20:02:19
>>461
テンプレートにしているから量産しようとしているとespしたんじゃない?
463:デフォルトの名無しさん
09/04/07 20:05:20
マヌケなespだな
464:デフォルトの名無しさん
09/04/07 20:12:33
どうでもいいがespがスタックポインタに見えてしょうがない
465:デフォルトの名無しさん
09/04/07 20:50:25
URLリンク(d.hatena.ne.jp)
ここで、
>「デストラクタがヘッダ中に記述されてしまっている」ことにある。
>更に言うと、「deleteがヘッダ中に行われてしまっている」ことが問題であり、
>よりつっこんで言うなら「deleteがCHoge::implの定義と別の場所で行われている」ことが問題なのだ。
>つまり、pimplにスマートポインタを使おうとするなら、デストラクタを必ず明示しなければならないのである。
>それも、implの定義(この場合はhoge.cpp)と同じ場所に、だ。
ってあるんだけど、その意味が分からない。
何でダメなの?
つーかコンパイルは一応通ったんだけど。
466:デフォルトの名無しさん
09/04/07 20:52:21
間抜けな設計に合わせてespのレベルも落としたんだろ
467:デフォルトの名無しさん
09/04/07 21:05:05
>>465
まず、「不完全型(名前だけ分かってるけど完全な定義がまだ見えていない型)のポインタのdeleteは危険」
であることを知ってほしい。これはコンパイルは通るけどきちんと動かないことがある。
(その型に自分で定義したデストラクタやoperator deleteがある場合、ちゃんと呼ばれない。)
class CHogeのデストラクタを記述しない場合、コンパイラが勝手に ~CHoge() を作る。
その中でスマートポインタである pimpl のデストラクタが呼ばれ、不完全型であるimplのポインタをdeleteしようとする。
468:デフォルトの名無しさん
09/04/07 21:13:26
未定義動作だからまともなコンパイラなら警告くらい出すはずだけどな
たまたまデストラクタもdeleteも定義してなかったからスルーしちゃったのかな
469:デフォルトの名無しさん
09/04/07 21:53:18
>>467-468
ありがとう。
「pimplがスマートポインタであるために特殊なdeleteが必要である。
だがコンパイル時にはpimplが不完全型であるためにその特殊なdeleteを呼び出すコードが作られない。」
ってことか。
となると、今回のケースでは
CHoge::~CHoge(){}
を自分で明示的に記述したとしても、それをhoge.hに書いている限りは解消されないんだよね。
hoge.cppのCHoge::implクラスの定義の後に自分で明示的に記述するならOKってことですかい?
470:デフォルトの名無しさん
09/04/07 22:00:43
>>469
前半は違う。スマートポインタであることは本質的な問題ではない。
pimplが単なるポインタであっても、 hoge.h でCHogeの定義の中に
CHoge::~CHoge() { delete pimpl; }
と書いたら、全く同じ問題が生じる。
後半はあってる。とにかく、明示的にであれ暗黙的にであれdeleteが出てくるところでは、
そのdeleteされるものの完全な定義が分かっていなければまずい場合があるということ。
471:469
09/04/07 22:25:09
>>470
なるほど。
根本的な問題は「デストラクタが云々」じゃなくて、
「不完全型のポインタのdelete」にあった訳か。
んで、その辺を全部気にせず丸投げしてもいけるのがshared_ptrなのか。
ありがとう。
・・・しかし
>>>468
>未定義動作だからまともなコンパイラなら警告くらい出すはずだけどな
VC++2008で試して見たのだが
>auto_ptrを用いた例ではVC++2008では警告しか吐かれない。
なぜか警告すら出てこなかったなぁ。
472:471
09/04/07 22:29:09
>>468
警告でた。
お騒がせしました。
warning C4150: 'CHoge::impl' 型を削除するため delete 演算子が呼び出されましたが、定義がありません。
: 'CHoge::impl' の宣言を確認してください。
473:471
09/04/07 22:33:37
追記:
g++でも警告出た。
note: neither the destructor nor the class-specific operator delete will be called,
even if they are declared when the class is defined.
bcc5.5.1では警告でなかった。
474:デフォルトの名無しさん
09/04/07 23:21:08
explicitをデフォルトコンストラクタに付ける意味はありますか?
また、explicitを引数を2つ以上取るコンストラクタに付ける意味はありますか?
475:デフォルトの名無しさん
09/04/08 00:39:21
1.デフォルト引数が付いてて、結果的に引数1個で呼べるなら意味がある
2.付けても害はないのでとりあえずコンストラクタには全部付けるポリシーにして付け忘れを防ぐ
476:デフォルトの名無しさん
09/04/08 01:14:57
explicitを付けさせる仕様でなく、
implicitを付けさせる仕様にすべき
477:デフォルトの名無しさん
09/04/08 03:43:39
>>476
いまさら仕様変更されても困るから、そうなってたらいいな、って話にしかならん。
478:474
09/04/08 07:09:56
>>475
なるほど。ありがとう。
479:デフォルトの名無しさん
09/04/08 19:07:19
copy-and-swapイディオムってすげーのな。
これって自作クラスのoperator=のオーバーロードの定義以外に使い道ある?
480:デフォルトの名無しさん
09/04/08 19:11:38
何がすごいの?
481:デフォルトの名無しさん
09/04/08 19:24:53
>>480
例外安全なところ。
482:デフォルトの名無しさん
09/04/08 19:39:37
>>479
コピーしないでスワップするだけなら、
参照型の引数で値を戻す場合にも。
void foo(hoge_t& result)
{
hoge_t x;
//xにあれこれ手を加える
swap(x, result);
}
まあ、何も考えなくていいときには、resultを直接いじることもあるけど。
483:デフォルトの名無しさん
09/04/08 20:12:23
全部正常に終わるまで変更を反映させたくない処理全般に使えるよね。
484:479
09/04/08 20:21:49
>>482-483
ほほー
ありがとう。
485:デフォルトの名無しさん
09/04/08 21:10:57
オーバーロードしたoperator=を
コピーコンストラクタの定義で使っても大丈夫?
486:デフォルトの名無しさん
09/04/08 21:34:30
よゆー
operatorほにゃららは普通の関数と全く同じように呼び出して可。
487:デフォルトの名無しさん
09/04/08 21:38:45
>>482
ドラゴン・スゴイコビッチ!(とてもすごいの意)
用件としては、自作クラスに swap 関数を装備することと、
その swap が例外を投げないようにすること?
488:485
09/04/08 21:49:40
>>486
ありがとう。
コピーコンストラクタ(に限らずコンストラクタ一般)から
メンバ関数を呼び出す時、
construct中なのにメンバ関数を呼び出しても
大丈夫なのだろうかと思ったのだ。。。
489:デフォルトの名無しさん
09/04/08 21:51:32
>>488
virtualなら気をつけないといかんかもしれんが
そうじゃないなら大概大丈夫
490:デフォルトの名無しさん
09/04/08 21:54:37
大丈夫
491:デフォルトの名無しさん
09/04/08 21:56:15
>>489
>virtualなら気をつけないといかんかもしれんが
ああ、
基底クラスのconstruct中にvirtualなメンバ関数呼ぶと
その基底クラスでの対応するメンバ関数が呼ばれるってやつね。
ありがとう。
>>490
ありがとう。
492:デフォルトの名無しさん
09/04/08 22:03:58
C++0xは本当に後 数ヶ月で策定されるんだろうか。
されたとして、ちゃんと動作するコンパイラが出て来るのはいつだろうか。
・・・うむ、心配だ。
493:デフォルトの名無しさん
09/04/08 22:35:04
別に心配することじゃない。
まともなコンパイラが出てから考えればいいこと。
早く出てくれないと困る事情でもあるのか?
494:デフォルトの名無しさん
09/04/08 22:50:26
すまぽとかは早く表順になってほしいなぁ。
もうすまぽを書くために何リットルのインクを消費したことやら。
(インク?)
495:492
09/04/08 22:52:55
>>493
>早く出てくれないと困る事情
いや、全然ないw
g++が速いかVCが速いか。
496:デフォルトの名無しさん
09/04/08 23:00:35
>>493
IntelC++は既にlambda関数がサポートされてるんだけど、IntelC++はコンパイル遅いんでdebugはVCでreleaseはIntelでやってるとlambda関数は使えなくて残念。
boost::lambda使えば済む話ではあるんだけど。
497:492
09/04/08 23:12:20
現在のTR1のライブラリ達は、正直なところ十分動作することが
確認されるまでは使わない方がいいんではないかと思うんだが。
それまではboostのが安心かなぁ。
でも標準に入ってる方が使うのは(気分的に)もっと楽になる事は確か。
498:デフォルトの名無しさん
09/04/08 23:56:20
class A{
public: virtual ~A() = 0;
};
class B :public A {};
class C :public B
{
public: ~C(){};
};
gccでundefined reference to B::~B()って怒られるんだけど、Bでd-tor書かないとダメ?
499:デフォルトの名無しさん
09/04/09 00:13:43
ごめん。純粋仮想d-torに定義書くの忘れてた
500:デフォルトの名無しさん
09/04/09 00:17:10
俺としては以下のやり方でMyClassクラスによるstd::swap関数テンプレートの特殊化を行い、
using std::swap;
swap(x,y);
で特殊化したstd::swap<MyClass>が呼び出せるかと思ったのだが、
以下のやり方だとなにか定義がかぶっているようなことを言われてエラーになってしまう。
再現するソースは次のようなもの。
//以下はMyClass.h
class MyClass
{
char *p;
public:
void swap(MyClass &hoge);
MyClass();
~MyClass();
};
//以下はMyClass.cpp
#include <algorithm>
#include "MyClass.h"
MyClass::MyClass():p("pointer"){}
MyClass::~MyClass(){}
void MyClass::swap(MyClass &hoge)
{std::swap(this->p, hoge.p);}
namespace std
{
template<>
void swap(MyClass &lhs,MyClass &rhs)
{lhs.swap(rhs);}
}
501:500
09/04/09 00:18:28
//以下はmain.cpp
#include <algorithm>
#include "MyClass.h"
int main()
{
MyClass x,y;
using std::swap;
swap(x,y);
return 0;
}
としたら、g++にて
MyClass.cpp:(.text+0x42): multiple definition of `void std::swap<MyClass>(MyClass&, MyClass&)'
main.cpp:(.text$_ZSt4swapI7MyClassEvRT_S2_[void std::swap<MyClass>(MyClass&, MyClass&)]+0x0): first defined here
collect2: ld returned 1 exit status
というエラーが出る。
どうしたらいい??
502:デフォルトの名無しさん
09/04/09 00:31:28
理由は覚えてないけどstd名前空間の中でswapの特殊化しちゃだめだった気がする。
ちょっと俺も確認してくるか。
503:502
09/04/09 00:33:03
別に駄目じゃないか。ごめんスルーしてくれ。
504:デフォルトの名無しさん
09/04/09 00:37:36
>>485
大丈夫だけど、普通operator =ってcopy (construct) and swapで書かない?
URLリンク(ja.wikibooks.org)(Copy-and-swap)
505:デフォルトの名無しさん
09/04/09 00:58:49
>>500
std::swapの特殊化はヘッダに書かないと駄目だろう。
main.cppでは特殊化したstd::swapが見えないから標準のstd::swapが実体化され
MyClass.cppで特殊化した物と衝突してるんだろう。
506:デフォルトの名無しさん
09/04/09 06:57:11
>>504
そうか。
コピーコンストラクタの定義に代入演算子を使うと定義が循環しちゃうのか。
507:500
09/04/09 06:58:19
>>505
なるほど。
std::swapの特殊化をヘッダに書く場合はinline指定しないと、
そのヘッダをインクルードするたびにまたmultiple definitionってなっちゃうかな?
508:デフォルトの名無しさん
09/04/09 08:13:54
>>507
いや、そういう話じゃない。
509:500
09/04/09 08:22:57
>>508
(1)main.cppでは特殊化した定義がその前になされていないから通常通り実体化。
(2)MyClass.cppでも特殊化した。
この(1)と(2)でmultiple definitionってことか。
つーことで
MyClass.hにstd::swapの特殊化を書く(1)
main.cppでMyClass.hをインクルード
ってこと?
510:508
09/04/09 08:24:06
>>507
あ、ヘッダに書かないといけないのは理解してるのか。ごめん
テンプレートの定義は inline じゃなくてもいいよ。 >500 の場合は inline が
適切だと思うけど。
511:デフォルトの名無しさん
09/04/09 08:25:44
これが inline じゃないといけないんなら全部の関数テンプレートが
inline にならないといけなくなるな。
512:インドリ
09/04/09 10:05:14
URLリンク(blogs.wankuma.com)
URLリンク(d.hatena.ne.jp)
513:デフォルトの名無しさん
09/04/09 10:18:24
>>512
広告ウゼェ
URLリンク(info.2ch.net)
> ・投稿者は、話題と無関係な広告の投稿に関して、相応の費用を支払うことを承諾します
514:デフォルトの名無しさん
09/04/09 10:19:49
しかもマルチかよ。何のつもりだ?
515:デフォルトの名無しさん
09/04/09 10:20:30
インドリしゃんに粘着する物好きもいるんですね
516:デフォルトの名無しさん
09/04/09 12:23:10
>>515
粘着の意味わかってんの?
517:デフォルトの名無しさん
09/04/09 14:28:38
C++でGUIのプログラムを作ろうと思うんだが、お勧め開発環境はなにかないか?
518:デフォルトの名無しさん
09/04/09 14:48:04
また環境も書かんと適当に訊くなあ。
519:デフォルトの名無しさん
09/04/09 14:51:01
>>518
OS;XP
520:デフォルトの名無しさん
09/04/09 15:00:29
C++Builder(8万円くらいする)
Turbo C++(C++ Builderの無料版 機能が削られていて少し古い)
Qt Creater(マルチプラットフォームのソフトが作れる コンパイルが遅い)
521:デフォルトの名無しさん
09/04/09 15:08:24
>>520
turbo c++でGUIって開発できるの??
522:デフォルトの名無しさん
09/04/09 15:52:24
できるよ
523:500
09/04/09 22:50:09
>>510-511
そういえば関数テンプレートの定義は
ヘッダに書くけど、それは普通の関数の類推で
inlineじゃなきゃいけないなんて考えちゃだめなんだったな。
Effective C++に書いてあったような気がしてきた。。。
ありがとうお二方。
524:デフォルトの名無しさん
09/04/09 22:53:28
「exit(0)で終了するとデストラクタが呼び出されたり呼び出されなかったりする」
っていうC++の仕様について学べるサイトを教えてください。
巻頭言 2000~
URLリンク(park1.wakwak.com)
一応ググったらこんなのがヒットしましたが、これ以外にも何かオススメをご存じであればお願いします。
525:デフォルトの名無しさん
09/04/09 23:10:23
std::powとかhypotとかをスレッドセーフに実行したいんだけど、おみゃーらどうしてる?
軽いに越したことはないずら
526:デフォルトの名無しさん
09/04/09 23:12:13
常識的に考えればスレッドセーフでないわけがない。
って書こうとしたが、errnoとか気にしている?
527:デフォルトの名無しさん
09/04/10 00:16:23
あれ?そうだったの?errnoは気にしてない。
うーん、じゃあ他のところで変な風になってたのかにゃ・・・?
ありがとうござんした
528:デフォルトの名無しさん
09/04/10 02:35:26
>>524 >>333-
529:デフォルトの名無しさん
09/04/10 08:30:05
errnoを気にするとどうなの?
530:デフォルトの名無しさん
09/04/10 11:55:32
>>529
errnoはグローバル変数なので、
errno = 0;
std::pow(x, y);
if (errno != 0) { /* 失敗 */ }
みたいなコードを書いたときに、powとifの間で他のスレッドによってerrnoが変更されてしまう可能性がある
だから、errnoを気にするとpowとかはスレッドセーフじゃなくなる
たいていのコンパイラにはerrnoをTLSに置いてスレッドセーフにするオプションとかがあるけどね
531:デフォルトの名無しさん
09/04/10 15:48:35
タクティカルレーザーシステム?
532:デフォルトの名無しさん
09/04/10 17:30:34
>>531
いやTrue Love Storyです。
じゃなくてThread Local Storageです。
533:デフォルトの名無しさん
09/04/10 18:05:46
元気でね 頑張ってね
手紙書くね たまに会えるよね
なんでかな 寂しいのに
寂しいよと 言えなかった
534:デフォルトの名無しさん
09/04/10 19:06:46
wwwwwwwwwwww
535:デフォルトの名無しさん
09/04/10 21:10:40
イイハナシダナー
536:デフォルトの名無しさん
09/04/10 22:17:52
>>530
よく分からんがerrornoへの代入って規格的に許されてたっけ?
537:デフォルトの名無しさん
09/04/10 22:27:30
18歳以上ならeroero挿入おkだよ
538:デフォルトの名無しさん
09/04/10 22:32:32
はいはいエロスエロス
539:デフォルトの名無しさん
09/04/10 23:13:49
18歳以上なのに、いつになってもeroeroの値がインクリメントされず初期値のままです。
540:デフォルトの名無しさん
09/04/11 00:09:13
>>539
君の中ではその変数は1つだけ存在すれば十分だよね。
俺達他人に迷惑書けて欲しくないから、君の実装から外には出さないで欲しいなぁ。
ってことでeroeroは自動的に0に初期化されてます。
541:デフォルトの名無しさん
09/04/11 00:15:47
E2BIGになって困る
542:デフォルトの名無しさん
09/04/11 00:39:57
>>540
static変数ってことか。
543:デフォルトの名無しさん
09/04/11 01:22:23
>>536
大丈夫です
C99(ISO/IEC 9899:1999)の7.5の脚注170に「むしろそうするべき」って書いてある(C++の規格には「Cの規格を見てね」って書いてある)
544:デフォルトの名無しさん
09/04/11 21:07:03
若干スレ違いな気がして申し訳ないんだが、
C++の書籍(他の言語は知らんけど)って正誤表無いor乏しいの多くない?
『Exceptional C++』を買ったんだけど、1ページ目から
誤植と思われる物があって困る。。。
だれか正誤表作ってくれている人とかコミュニティとか無い??
545:デフォルトの名無しさん
09/04/11 21:34:26
グローバルスコープに
std::string foo();
って書いたら、
std::string型を返す、引数のない、fooという名前の関数の宣言になるの?
それとも
std::string型のfooという変数の宣言とデフォルトコンストラクタ呼び出しになるの?