トップページ⇒tech
987コメント354KB

C++相談室 Part4

■ このスレッドは過去ログ倉庫に格納されています
0001デフォルトの名無しさんNGNG
v(^・^)v

Boost C++ Libraries
http://www.boost.org/
C++ Final Draft International Standard
http://www.kuzbass.ru/docs/isocpp/
GotW.ca Home Page
http://www.gotw.ca/
STLport
http://www.stlport.org/

C++相談室
http://piza.2ch.net/tech/kako/980/980175292.html
C++相談室 Part3
http://pc.2ch.net/test/read.cgi/tech/1003832761/l50
0153デフォルトの名無しさんNGNG
>152
チョメチョメ に一票

シーチョメチョメマンセー
0154名無しさん@お腹いっぱい。NGNG
g++の標準入出力ストリームについて質問です.
ifstreamを用いて,同じファイルから2回データを読み込みたいとき,
例えば1回読み込んだあと,
seekgを用いてカレントポジションを先頭に戻し,再び読み込む,即ち
#include <iostream>
#include <fstream>
using namespace std;
int main ()
{
char tmp;
ifstream ifs ("hoge.txt");
// 1回目読み込み
while (!ifs.eof ()) {
ifs.get(tmp);
cout << tmp; // 例えば,表示.
}
ifs.seekg (0, ios::beg); // 開始点にシーク
ifs.clear (); // フラグを初期化
// 2回目読み込み
while (!ifs.eof ()) {
ifs.get(tmp);
cout << tmp; // 例えば,表示.
}
return 0;
}
のように書けますよね.
同様に,標準入力(catとパイプでつなぎたい)から2回データを読みたいと思いまして,
#include <iostream>
using namespace std;
int main ()
{
char tmp;
// 1回目読み込み
while (!cin.eof ()) {
cin.get(tmp);
cout << tmp; // 例えば,表示.
}
cin.seekg (0, ios::beg); // 開始点にシーク
cin.clear (); // フラグを初期化
// 2回目読み込み
while (!cin.eof ()) {
cin.get(tmp);
cout << tmp; // 例えば,表示.
}
return 0;
}
としたところ,うまくいきません.
で,cin.tellg ()を使いましてseekg (0, ios::beg)でカレントがどこに移ったか調べましたところ,
どうやらifstreamの場合と挙動が違うことが分かりました.
つまり,ifstreamではseekg (0, ios::beg)によりカレントポジションが最初の位置に戻りますが,
istream (この場合cin)では戻らないようです.
これは,こういう仕様なのでしょうか? それとも,使用しているライブラリの不備なのでしょうか?
(派生関係にあるのだから,同じように動いて欲しいものです.) 私が使用している環境は,
$ g++ -v
Reading specs from /usr/lib/gcc-lib/i386-redhat-linux/2.95.3/specs
gcc version 2.95.3 20010315 (release)
です.
0155デフォルトの名無しさんNGNG
>>152
マジレスしちゃいかんのかな?
「++」はインクリメントじゃ。
0156デフォルトの名無しさんNGNG
それではこれから「C++」は「Cインクリメント」ということで。
0157デフォルトの名無しさんNGNG
>>154
pipeの仕様。
0158デフォルトの名無しさんNGNG
>>152
マジレスしちゃいかんのかな?
(++)は困ったときの顔文字じゃ。
(+π+)とする人もいる。
0159デフォルトの名無しさんNGNG
C++ ← しぃぷるぷる
0160名無しさん@お腹いっぱい。NGNG
>>157
>pipeの仕様。

どうやら,最終点まで読み込む前だったら,
seekg (0, ios::beg)は効くみたいです.

例えば,1バイトだけ読み込み,seekg (0, ios::beg)で
先頭に戻したあと,再び読み直す以下のようなプログラム
#include <iostream>
using namespace std;
int main ()
{
char tmp;
// 1バイト読み込んで表示
cin.get(tmp); cout << tmp;
cin.seekg (0, ios::beg); // 開始点にシーク
cin.clear (); // フラグを初期化
// 最初から読み直し
while (!cin.eof ()) {
cin.get(tmp);
cout << tmp; // 例えば,表示.
}
return 0;
}
で,1バイトより大きなデータを標準入力に与えると,
ちゃんと先頭の1バイトも表示し直してくれました.

最終点まで読み込むと標準入力ってバッファを消去してしまうってことなのかな?
0161デフォルトの名無しさんNGNG
>>160
iostreamが管理しているバッファにおさまる限りはseekできるってことでは?
1MBくらい読んでからseekgしてみれば失敗するはず。
seekgが下請けに使ってるlseek(2)はpipeには使えないのよ。
0162名無しさん@お腹いっぱい。NGNG
>>161
>1MBくらい読んでからseekgしてみれば失敗するはず。
>seekgが下請けに使ってるlseek(2)はpipeには使えないのよ。

試してみたら,おっしゃる通りでした.
4096バイトまでは遡れるけど,4097バイトでは失敗しました.
どうもっ!
0163名無しさん@お腹いっぱい。NGNG
162です.

ついでに,
たとえ4096バイト以内でも,
最終地点に到達したら,seekgは失敗してしまうようです.

まぁ,いずれにしても標準入力に対してはseekgは使えないみたいですね.
0164ロリオタ殺すNGNG
Reported by WPNP
Tuesday, January 01, 2002 20:11:46

User Name: TenTen_DWP2f3e793d1a2b
Access Level: user
Time Online: 5:55:17
In Channels:
Status: 11 in queue (-2 of 0 available)
Shared Files: 120
Active Downloads: 2
Active Uploads: 2
Connection Type: DSL
Client Version: WinMX v2.6j


ロリと盗撮と援交・・・・・・・・

web pageはこちら。
ttp://www.tokyo-nazo.net/~tenten/

キーワード
援助交際白書
ディズニーランドトイレ
ロリータ写真集
0165デフォルトの名無しさんNGNG
誤爆か?
0166_NGNG
テンプレート関係が1番完璧に処理できるコンパイラはどれですか?
今VC使ってるけどBC++Builderとかg++とかどうですか?
0167デフォルトの名無しさんNGNG
>>166
VC6 << Borland C++ Compiler < g++

ただ GCC は細かいところでバグがある感じ。ネームスペースとテンプレートを絡めて使うと、
たまに挙動が変。
0168_NGNG
>>167
ありがとうございます。
Vine Linuxいれたからg++でもやろうかな。
VCでSTLを深くやろうとしたり、テンプレート関係の本のサンプルを打ち込んでも
変な場合があってやる気がなえてたところだから。
Borland C++ Compiler はC++Builderの純粋なコンパイラ部分なんだよね。
GUIのプログラム作るのが楽そうだからこっちもよさそうだな。
0169167NGNG
>>168
template らぶらぶ で GUI のプログラムを組むのなら VC6 + ATL/WTL を推しときますが。
VC6 の template は「完璧」からは程遠いですが、実用的なフレームワークを作れる程度に
は機能します。
0170デフォルトの名無しさんNGNG
ゲイツ社のC++と、ボーランドのC++ビルダーはどう違うのですか?
0171デフォルトの名無しさんNGNG
>>170

ゲイツ社のC++ってVC++のことか?
ソフトが違うじゃん。
0172デフォルトの名無しさんNGNG
C++BuilderのコンパイラよりもVC++のコンパイラの方が最適化が優れている気がするけどどうなんだろう。
0173デフォルトの名無しさんNGNG
>>172 その通り、最適化コードの質はVCの圧勝。でも言語規格準拠度はVCのボロ負け。
0174デフォルトの名無しさんNGNG
>>173
VS.NETで改善されてるみたい。
0175173NGNG
VS.NET(VC7)で規格準拠もOKとの噂は聞くけど実際のところ、どう?
どこかに比較記事とかあったら紹介希望。
# RCなしでbeta2からいきりなりリリースとは勇気あるなぁ>VS.NET
0176デフォルトの名無しさんNGNG
なんつーんだろ。
for文の初期
0177デフォルトの名無しさんNGNG
>>175
英語版はRC出てたはずでは?
0178デフォルトの名無しさんNGNG
VS.NET日本語版の正式な発売日・価格ってまだでないの?
0179デフォルトの名無しさんNGNG
>>177 おや英語版のRCって出てたっけ?ちゃんと届けろよ>MSDN
0180デフォルトの名無しさんNGNG
ちょっと質問良いですか?

string型の変数をchar型の配列に変換するにはどうしたら良いんでしょうか?
0181デフォルトの名無しさんNGNG
>180
c_str()
0182デフォルトの名無しさん NGNG
すいません教えてください。
ウインドウの作成と初期化、さらにダイレクトXの初期化をするクラスを
作ろうとしているのですが、WindowProc()関数をそのクラスのメンバ関数に
するにはどうすればいいのでしょうか?
WM_DESTROYメッセージの後にダイレクトX関連のオブジェクトをリリースする
必要があるのでどうしてもWindowProc()関数内部からそのリリースする
メンバ関数にアクセスしたいのです。
よろしくお願いします。
0183デフォルトの名無しさんNGNG
・static/global変数でthisを設定しておく
・hWnd -> thisの連想配列で処理する(MFC式)
・hWndをthisにすげ替えるWindProcを自動生成する(ATL式)
お好きなのをどうぞ。
0184182NGNG
うーむ。正直サッパリです。どこか参考になるWEBとか
ありませんか?もしくはウインドウ作成と初期化を一つにまとめた
クラスのソース公開しているところとか。
0185デフォルトの名無しさんNGNG
>もしくはウインドウ作成と初期化を一つにまとめた
>クラスのソース公開しているところとか。

なぜATLのソースを読まないのでしょう?
0186182NGNG
うーん。ひよっこどころか卵状態なのでATL自体よく分かってないです。
0187デフォルトの名無しさんNGNG
>>184
ttp://www.sun-inet.or.jp/~yaneurao/
0188デフォルトの名無しさんNGNG
>>183
CreateWindow 直後に SetWindowLong() で this ポインタを HWND に関連付け、ウィンドウプロシージャでは
GetWindowLong() で this ポインタを引き出してきてメンバ関数を呼び出す、ってのもアリかな。

>>186
MSDN Library に「ATL 3.0 ウィンドウクラス入門」という文書があったはず。あれ読んで CWindowImpl 使うの
が楽だと思うぞ。
0189182NGNG
とりあえず187のページのSDKダウンロードして
目的のソース見つけました。あとそのページでかなりプログラム技術が
アップしそうな気がします。どうもありがとうございました。
ATLは適当に調べたかんじではまだよく分からなかったので
後回しにします。
0190デフォルトの名無しさんNGNG
>>189 その >>187のページって「やねうらお」だね。
内容見てないけど大丈夫かいな。ATLのソースみた方が安心だと思うぞ。
0191デフォルトの名無しさんNGNG
>>190
技術そのものは、あちこちからパクってきたものだから問題ないんじゃない?
(変にオリジナリティを出そうとしてがんばって改悪してるかもしれないけど)
0192デフォルトの名無しさんNGNG
>182
この板には>>190-191みたいなアンチやねうら粘着厨房がいるみたい、
気にしない方がいいYO!
0193デフォルトの名無しさん NGNG
>192
レス早いですね
粘着厨房さんですか?p
0194デフォルトの名無しさんNGNG
やねうらって誰?
0195デフォルトの名無しさんNGNG
やねうらおがだれだかのコードをパクって、自分の掲示板で指摘されて
ハジかいたってのは見たことある。
それ以外はよく知らないけど。
0196デフォルトの名無しさんNGNG
>>189
やね氏の能力は否定しないが、
文章を読んで賛美者になったりしてはいけない。
自分で技術的真偽の判別がつかない初心者は気をつけるように。
0197デフォルトの名無しさんNGNG
>>195
タスクコンテクストスイッチに関して、かなりボケたことを言ってて叩かれてたのはリアルタイムで
見てた。最近はどうか知らないけど、当時は「計算機論理設計の基礎が分かっちゃいねぇ、ヘネ
シー&パターソン読んで出直せ」というレベルではあった。

C++ と関係ないから、これ以上、やねうらおを語りたければプログラマー板行きましょう。
0198190NGNG
>>197 賛成〜。やねうらお語るほどヒマじゃないけど、
Webの技術情報を安易に信用するなってことで。
0199デフォルトの名無しさんNGNG
STLのvector(or その他)について質問。

まず<やりたいこと>

・配列をvectorに置き換えたい。
・でも、配列先頭へのポインタによるアクセスは同じようにしたい

よーするに、T Array[5];をvector<T> Array;にしたいんだけど、 (void*)Arrayって
アクセスもしたい、っつーことなんです。

これ、const_pointer使えばOKなん? それとも、クラス書かないとダメ?
0200デフォルトの名無しさんNGNG
大抵の実装では、vector<T>::iteratorがT *になるはず‥‥
ポインタの方で、要素を追加したりしないなら、こういう手もあり。
まぁ、それを想定するのが卑怯だというなら、クラスを実装
するしかないね。
0201199NGNG
うを、素早い(^^;

ということで早速のお返事、ありがとうございます。

>大抵の実装では、vector<T>::iteratorがT *になるはず‥‥
つーコトは、そのまんま(void*)ArrayでOK?(^^;
ちなみに、
>ポインタの方で、要素を追加したりしないなら、こういう手もあり。
なんてことは露ほども考えておりません(^^;
ぶっちゃけて話しちゃうと、DirectX8のDrawPrimitiveで使う頂点配列を、何とかして整理したかったのココロ(^^;
0202デフォルトの名無しさんNGNG
>>199
std::vector<T> v;
T* p = &v[0];

vector は C の配列と同様のメモリ配置になることが規格上保証されてるから、これで OK。C で書かれた
関数と C++ 混ぜて使う場合 vector は重宝します。

>>197
そういや、以前の yaneSDK には std::vector に auto_ptr っぽいセマンティクスを持つ型を格納するという
おおぼけなコードがあった。最近のは見てないから知らんけど。
0203デフォルトの名無しさんNGNG
>>202
> vector は C の配列と同様のメモリ配置になることが規格上保証されてる
これって、規格になったんだっけ。まあ、そういう方向で標準化作業は
すすんでいたと思うので、そうでない実装というのは存在しないだろうけど。
0204デフォルトの名無しさんNGNG
>>200
g++ 付属の stl だと、vector<T>::iterator から T * への暗黙の変換は
定義されていなかったと思う。
0205デフォルトの名無しさんNGNG
>>204
vector<T>::iterator から T* への変換とかいう問題以前にさ、
typedef T* iterator
ってなってるはずなんだが。

今、g++ の vector のヘッダ見てみたけどさ、ちゃんと

typedef _Tp value_type;
typedef value_type* iterator;

ってなってるぞ。
0206199NGNG
っと、ごめんなさい。テンプレート付きのクラスでメソッドを記述するには
どうしたらいいのでしょう?

#include <vector>
using namespace std;

template <class T> class apexVector
{
public:
//頂点データのベクタ
vector<T> apex;

void apexVector::method1();

};

vectorは(void*)apexが出来るっつーのでpublicにして横着しようと思ったなり(^^;

が、それは置いておいて、method1でコンパイルエラーになります。apexVector::を
取っ払えばとりあえずコンパイルは通りますが、ここは本来はどーゆー風に書くのでしょう?
0207デフォルトの名無しさんNGNG
ふむ。君はvectorのソースも見ないんだな‥‥ まぁそれはいい。
template <class T> class apexVector {
 void method1() { // 実装
 }
 void apexVector<T>::method2(){//実装
 }
};
ということをやればよい。ああ、テンプレートのメソッドが、テンプレート外に
記述できない、というのは知っているだろうな。(.cppと.hに分離できねーとか
泣きついてくるなよ)
0208デフォルトの名無しさんNGNG
>>203>>205
VC7は違うらしいYO
0209デフォルトの名無しさんNGNG
>>207
template <class T> class apexVector {
 void method1() { // 実装
 }
 void method2();
}
void apexVector<T>::method2(){//実装
}
こうじゃないの?
0210デフォルトの名無しさんNGNG
あ、method2()の実装のまえにtemplate<class T>が必要。
0211199NGNG
>>207

>ふむ。君はvectorのソースも見ないんだな‥‥ まぁそれはいい。
厨房で申し訳ないっす(^^;

>template <class T> class apexVector {
〜中略〜
>ということをやればよい。ああ、テンプレートのメソッドが、テンプレート外に
>記述できない、というのは知っているだろうな。(.cppと.hに分離できねーとか
>泣きついてくるなよ)

……知りませんでした、申し訳ない(^^; 「.hと.cppに分離」はC++の作法だと思っておりましたので(^^;
早速やってみます。アドバイス多謝(拝)
0212デフォルトの名無しさんNGNG
>>205
gccのvectorのiteratorはT*との互換性はない、と書いた文書を
俺もどこかで見たぞ。公式の文書で。

古いの見てるんじゃないのか? libc++-v3じゃないやつとか。

それと、O(1)のオーダーでアクセスできることと
C の配列と同様のメモリ配置になることとは違うぞ。
0213デフォルトの名無しさんNGNG
少なくともg++-2/stl_vector.hとg++-3/stl_vector.hでは
typedef value_type* iterator;
となってる。
0214デフォルトの名無しさんNGNG
http://gcc.gnu.org/onlinedocs/libstdc++/faq/index.html#5_1
これだな。
0215デフォルトの名無しさんNGNG
どうでもいーことだけど、みんな
template<class T>
て書く?
template<typename T>
て書かない?
0216デフォルトの名無しさんNGNG
面倒っちいから template<class T> って書くよ
0217デフォルトの名無しさんNGNG
>>202
>std::vector<T> v;
> T* p = &v[0];
> vector は C の配列と同様のメモリ配置になることが規格上保証されてるから、これで
> OK。C で書かれた関数と C++ 混ぜて使う場合 vector は重宝します。

std::vector<T> v;
T& r = v[0];
でなんか問題あるのか? ここでポインタわざわざ使う必要性が見えないんだが。
0218デフォルトの名無しさんNGNG
>>217
「C で書かれた関数と C++ 混ぜて使う場合」があるからなんでは?
0219デフォルトの名無しさんNGNG
>>213
gcc-3.0.2/include/g++-v3/bits/stl_vector.h だと、
typedef __normal_iterator<pointer, vector_type> iterator;
になってるね。__normal_iterator は別のファイルでクラステンプレート
で定義されてる。
0220217NGNG
>>218
その「Cで書かれた関数」というのが、「ポインタを引数に取る関数」の
ことならまあ納得するけど、「CとC++を混ぜる」場合、C++上でしかありえ
ないのにC的にする意味は無いと思うが。CにもC++にも適用したいアルゴリズム
はポインタよりイテレータの文脈で処理すべきだ。
0221デフォルトの名無しさんNGNG
>>211
>……知りませんでした、申し訳ない(^^; 「.hと.cppに分離」はC++の作法だと
つーか、それは MS の作法なんじゃねーの? 不必要に情報をタレ流さない
ためには、やたらと .h を作らないほうがいいと思うんだが。

あと、テンプレートクラスを .h で定義しておいて、そのメソッドを
.cpp で実装する、ということは可能だよ。export が使えれば一発だが、
これが使えなくても、必要に応じて明示的なインスタンス生成というのを
やればよい。
0222デフォルトの名無しさんNGNG
>>220
DirectX みたいな「与えられた API」を使ってプログラムを組む場合には、C++ を使っていてもポインタに
縮退させること必須でしょうが。文脈読めよ。
0223デフォルトの名無しさんNGNG
>>222
どして? その元の話がvectorを使おうとしてる以上DirectX云々は
副次的な文脈だろ。ちなみに俺の回答は「そんなとこでvector
使うんじゃねえヴォケ!」
0224デフォルトの名無しさんNGNG
>>223
> 「そんなとこでvector 使うんじゃねえヴォケ!」
なんで?
0225デフォルトの名無しさんNGNG
>>223
STL は C との相互運用にも十分に配慮されたライブラリだから、使わない手はないと思うが。もし英語が
苦手でなければ Scott Mayers の Effective STL を買ってきて Item 16 "Know how to pass vector and
string data to legacy APIs." を読むことを薦めとく。
0226デフォルトの名無しさんNGNG
>>215
Modern C++ Design で、
クラス(ユーザー定義型)しか使わないなら class
組み込み型も使う可能性があるなら typename
っていうふうに使い分けてた。

>>219
いわゆる type traits ってやつかな。
__normal_iterator<pointer, vector_type> を展開すると結局ただの valuetype* になりそうな気がするんだけど。
0227デフォルトの名無しさんNGNG
>>223 なんでかなー、vector 使って良いじゃん。
extern "C" の既存関数やAPIに対して、
std::string の持つデータを .c_ptr() や .data() で渡すのと同じでしょ。

それとも、vector<T> のかわりに basic_string<T> を使えという
主張ですか?それなら納得するけど。
0228無名λ式NGNG
>>168
g++は、version3以上じゃないと、VC++6よりtemplateはへぼい。そこに注意。
0229デフォルトの名無しさんNGNG
>>219
gcc の STL は読んでないので知りませんが、他の有名どころだと STLport の vector<T>::iterator がデバッグ
モード限定で T* ではないですね。

話がそれるけど STLport のデバッグモードは無効な iterator 参照などを簡単に発見できて便利です。T* な
iterator だと、元の vector に push_back しても iterator が正しい領域を指しつづけることが多いから、バグを
埋め込んだときに再現率が低くて泣ける。
0230デフォルトの名無しさんNGNG
>>225
>>>223
>STL は C との相互運用にも十分に配慮されたライブラリだから、使わない手はないと思う
>が。もし英語が苦手でなければ Scott Mayers の Effective STL を買ってきて Item 16
>"Know how to pass vector and string data to legacy APIs." を読むことを薦めとく。

やむをえない時にやるべきことと、率先してやるべきことを混同していないか?
スタック上とか任意の場所にメモリを置いていたいときにvectorだと簡単に管理
できないし、相手先のC関数の挙動とvectorの実装が完全に見えている(=カプセル化
されていない)状況でしか使えないというのはバグの温床以外の何物でもない。
せめて間にラッパ入れてやらないと。
0231デフォルトの名無しさんNGNG
>>230
スタック(というか自動変数)として vector とるのはまったく問題ないけど。その場合でもデータそのものは
allocator 経由で(一般には)ヒープ上に取られた領域に置かれるけど、その違いが問題になるケースって
あるなぁ。

考えられるのは API 内部で渡されたデータに対して free() したり realloc() するケースだけど、それは

 生成 破棄 利用

いずれも専用の API 群で行う設計で、そもそも vector 使う余地がないし。

> 相手先のC関数の挙動とvectorの実装が完全に見えている(=カプセル化されていない)状況でしか使え
> ないというのはバグの温床以外の何物でもない。
問題になるような関数の例を希望。

あと vector の実装に関して仮定していることは「データが連続領域にとられること」だけで、特に問題ない
と思う。

> やむをえない時にやるべきことと、率先してやるべきことを混同していないか?
C++ だと malloc() で確保した生のメモリ領域を自前で管理せず vector を使うのは「率先して」やるべきこと
でしょう。例外中立/安全な可変長のストレージを作ろうとすると、結局 vector と同じような実装にいきつく
ことになるし。
0232デフォルトの名無しさんNGNG
>あと vector の実装に関して仮定していることは「データが連続領域にとられること」だけ

これ、
C++ Final Draft International Standard
http://www.kuzbass.ru/docs/isocpp/
に載っていますか? ちいさいデータなら並んでるかもしれませんが大きな
データは簡単に確保できず断片化されるとかあるんじゃ、と思ったんで。
0233デフォルトの名無しさんNGNG
vectorの意図しているのは可変長配列であって、
バッファではないよ。バッファとして使いたいなら本来は
それ用のクラスを作って使うべき。もしくはget_temporary_bufferを使うか。
理念でなく実利で言うなら、要素のコンストラクトがおこるとかもある。

>問題になるような関数の例を希望。

について言えば、明らかにカプセル化の理念を無視してるわけだから、
例なんかなくても一見してだめ。

もっとも、俺自身は「わかってやってるならよし」という立場だけど。
0234227NGNG
あっさり無視されたんでもう一度書くけど
>>233 バッファとして使うなら basic_string<T> ではだめかね
0235デフォルトの名無しさんNGNG
stringのc_str()とかdata()って、新しい領域を内部でnewしてるんじゃないかと
怖いんだけどそんなことってない?
0236デフォルトの名無しさんNGNG
>>235 コピーした直後とか、部分文字列として取りだした直後は、
内部で new してる可能性があるね。でもなぜそれが怖いの?
0237デフォルトの名無しさんNGNG
>>232
それだと vector と deque を分ける意味がないと思うけど。

規格にざっと目を通してみたけど、vector のデータが連続領域にとられることを明記してる文章は
見当たらんね。Effective STL には p.74 に

 The elements in a vector are constrained by the C++ Standard to be stored in
 contiguous memory, just like an array, ...

と書いてあるけど。

>>234
名前が basic_string だから文字列にしか使えん、と思ってる人多数に一票。わりと使いでのある
クラスなんだけどね。
0238デフォルトの名無しさんNGNG
>>233
> 明らかにカプセル化の理念を無視してる
どこが? vector の内部データ形式を仮定してるところかな。

basic_string は値の「共有」を可能にするために参照カウンタが入ってることが多いよね。書き換えが少ない
(でも書き換えないわけじゃない)小規模なデータを値として渡していく場合には便利だけど、DirectGraphics
の頂点リストを管理するには不適切と思うな。

っつかバッファでもサイズが大きくなったら basic_string 捨てて rope だと思われ。標準じゃないけど。
0239デフォルトの名無しさんNGNG
ropeって、その安直なネーミングが萌え
0240デフォルトの名無しさんNGNG
>>236

Cスタイル関数に渡すのにc_str()して、それが何万回も呼び出されると考えると、
newされるのは勘弁して欲しい
0241デフォルトの名無しさんNGNG
>>240
性能に関しては、プロファイラにかけてボトルネックになってることを特定してから考えれば良いと思う
けど。

ちなみに VC6 添付の STL や STLport, あたりだと、内部で C 形式の文字列データを使ってるので、
c_str() は

  return this->internal_buf_ptr;

みたいなコードになってる。コストは this 経由の間接参照が一つ入るだけ。gcc 2.95.3 の STL だと

const charT* c_str () const
{ if (length () == 0) return ""; terminate (); return data (); }
charT* data () { return reinterpret_cast<charT *>(this + 1); }

と末尾を eos で埋める terminate() 呼び出しが入るけど、それを除くとコストはやっぱり間接参照ひとつ分。
0242236NGNG
>>240 c_str() 呼出毎に毎回 new は無いから安心しな。必要に応じて new するだけだよ。
言語規格上は毎回 new しても構わないが、まともな実装ならそんなことはしない。
0243デフォルトの名無しさんNGNG
memcpy( const_cast<char*>(stringVar.data()), ***, ***)
みたいなことをよくするので(他にはfreadとか)、いちいちnewされたら困る。あと、こういう実相依存なプログラムしてるといつか困るとは思う。
0244236NGNG
>>243 はぁ〜、const外したらマズイしょ。しかも memcpy …
stringの保持データ操作には
string::assign(const charT*, size_type) や
string::replace(size_type, size_type, const charT*) を使っておくれ
fread に渡すのは auto 変数のバッファにし、後で assign/append しておくれ
0245199NGNG
ううっ、ついていけないほどの高度な議論になってる……(^^;

とりあえず、
std::vector<T> array;
void* p = &(array.at(0));

で、

T array[5];
void* p = array;

と同じ動作になりました。アドバイスしていただいた皆さんに感謝(拝)
ちなみにクラス定義はメソッド実装も含めて全部.hに集約したナリ。
軟弱でソマソ(^^;

ちなみに、VC++ Ver.6のSTLには、メモリ不足時にかなり致命的なバグが
あるとゆー話を聞いたのですが本当?
なんでも、メモリ確保に失敗したら例外出さずにreturn 0;するとか……(^^;
0246デフォルトの名無しさんNGNG
>>245
STL に限らず、VC++6.0 の new はメモリ確保に失敗しても例外投げないよ。
set_new_handler の仕様も標準のものと全然違う。
0247デフォルトの名無しさんNGNG
>>245
バグというか、仕様ですね。operator ::new(size_t) 失敗時に呼び出すハンドラを _set_new_handler() で指定
できるので、そこで対処してください。
0248何で検索すればいいんでしょうか(´д`;NGNG
int型の値ををChar型に投げたいんですが

int i = 3;char c;
c = i;

としたとき、
cの値が'\003'ってなるのですが、原因がわからず妙な所で苦戦しています。
だれか助けてください・・・
0249デフォルトの名無しさんNGNG
今日は盛況だねー
>>243
>memcpy( const_cast<char*>(stringVar.data()), ***, ***)

それっぽいのは俺もよくやる。WindowsだとconstになってるべきAPIが
constじゃない場合があるからその場合は仕方なく...とか思ったら
コピー元じゃなくコピー先かよ。氏ね
0250248NGNG
う・・・もしや文字コードが3になってるだけか・・・
0251デフォルトの名無しさんNGNG
>>250 その通り。きみのやりたいことは c = i + '0'; で実現できるね。
0252デフォルトの名無しさんNGNG
>250
正解!!オメデトウ!

まぁお主のやりたい事は sprintf を使うのがてっとり早いかな.
# フレーム合戦はヤめような(藁 > all

■ このスレッドは過去ログ倉庫に格納されています