【初心者歓迎】C/C++室 Ver.57【環境依存OK】

このエントリーをはてなブックマークに追加
1デフォルトの名無しさん
エスケープシーケンスやWin32APIなどの環境依存なものでもOK。
ただしその場合、質問者は必ず環境を書きましょう。
※sage禁止です(と代々スレに書いてありますが自己判断で)。

【前スレ】
【初心者歓迎】C/C++室 Ver.56【環境依存OK】
http://pc11.2ch.net/test/read.cgi/tech/1215278693/

【アップローダー】(質問が長い時はココ使うと便利)
http://kansai2channeler.hp.infoseek.co.jp/cgi-bin/joyful/joyful.htm

◆ソースのインデントについて
半角やTABでのインデントはスレに貼ると無くなります。
そのため、アップローダーに上げるのが最も良いですが、
直接貼るのであれば、全角空白か に置換しておくことをお勧めします。
2デフォルトの名無しさん:2008/07/16(水) 22:40:18
しまった。コピペしてそのままにしてしまってた・・・。
正しくはこうだな。

◆ソースのインデントについて
半角やTABでのインデントはスレに貼ると無くなります。
そのため、アップローダーに上げるのが最も良いですが、
直接貼るのであれば、全角空白か に置換しておくことをお勧めします。
3デフォルトの名無しさん:2008/07/16(水) 22:58:04
           
4デフォルトの名無しさん:2008/07/16(水) 23:58:32
int main(int argc, char *argv[])
{
  FILE *fp;

  if(fopen_s(&fp, "hoge.txt", "w")) exit(1);
  fwrite("hoge", 4, 1, fp);
  fclose(fp);

  return 0;
}

これを普通に実行するとちゃんとファイルが作成されるのですが、アイコンにファイルをドロップして始めるとファイルが作成されません。
なにか制約でもあるのでしょうか?
5デフォルトの名無しさん:2008/07/17(木) 00:03:13
>>4
どこか、あなたの知らないところに作られています。
フルパスでファイルを作るか、カレントディレクトリを指定すると宜しいかと。
6デフォルトの名無しさん:2008/07/17(木) 00:09:10
>>5
ありがとうございます。わけの分からないところに作られていました。
デフォルトでカレントディレクトリに作られると勘違いしていました。
7デフォルトの名無しさん:2008/07/17(木) 05:42:31
class Hoge
{
Hoge() { Init(); }
~Hoge();
Init();
}

このようにコンストラクタ時に
初期化用のメンバ関数を用意して使うことはokなのでしょうか。
8デフォルトの名無しさん:2008/07/17(木) 05:48:51
ok
9デフォルトの名無しさん:2008/07/17(木) 05:57:10
ありがとうございました。
これで長々と書かずに済みます。
10デフォルトの名無しさん:2008/07/17(木) 08:00:28
>>7
Initはvirtualにしないことだけ気をつけて。
11デフォルトの名無しさん:2008/07/17(木) 08:19:59
>>6
いや、カレントディレクトリに作られているはずだよ。
カレントディレクトリが予想外な場所になっているだけで。
12デフォルトの名無しさん:2008/07/17(木) 08:43:07
オープンソースのdllなんかを改造して
自分でコンパイルする時
デバッグモードでやるのとリリースモードでやるのでは
どういった違いがでるのでしょうか?
13デフォルトの名無しさん:2008/07/17(木) 09:09:55
デバグ情報
最適化
14デフォルトの名無しさん:2008/07/17(木) 09:23:44
本当のプロはデバッグモードは使わない。
1512:2008/07/17(木) 09:34:57
デバッグ情報っていうのは、どういう場面発生して、どうしたら使えるんでしょうか?
16デフォルトの名無しさん:2008/07/17(木) 09:40:29
デバッグ情報がある場合:
gdbとか使ってると、Segmentation Falutなんかが出たときに、
その場所をソースコードの行番号で教えてくれる。
17デフォルトの名無しさん:2008/07/17(木) 10:37:12
動的解析ツールでも、デバッグ情報があれば行単位で結果を出せるね。
そうでないと、アセンブラのインストラクション単位になってしまう。
18デフォルトの名無しさん:2008/07/17(木) 14:23:26
VC++ 6で作成したものをVC++2005で開いてビルドすると
 long lTemp = timeStamp.ulSeconds;
 char* pszTemp = ::ctime( &lTemp );
のところで
 error C2664: 'ctime' : 1 番目の引数を 'long *' から 'const time_t *' に変換できません。(新しい機能 ; ヘルプを参照)
 指示された型は関連がありません。変換には reinterpret_cast、C スタイル キャストまたは関数スタイルのキャストが必要です。
とでてしまいました。
それで
 char* pszTemp = ::ctime((time_t *) &lTemp );
と書き替えたらビルドは通ったのですが、これで問題ないのでしょうか?
19デフォルトの名無しさん:2008/07/17(木) 14:28:20
lTempの値次第
20デフォルトの名無しさん:2008/07/17(木) 14:54:24
>>10
virtualにしてもコンストラクタ内からだと無視されなかったっけ?
21デフォルトの名無しさん:2008/07/17(木) 14:59:10
>>18
time_t の大きさ確認してみ。最悪変なところ書き換えるかも。
VC2005から、時間関係がデフォで64bitになってる。
32bitにするのはなんかマクロがあった。
22デフォルトの名無しさん:2008/07/17(木) 15:24:47
>>18
要は、lTempをtime_tにしておけってこった。但し、tieStamp.ulSecondsの仕様に注意な。

>21はどうやらconstが目に入らなかったらしいが。
23デフォルトの名無しさん:2008/07/17(木) 16:21:55
C言語のソースからC++で定義されている関数を呼びたいのですが
やはり無理でしょうか?
2423:2008/07/17(木) 16:25:59
すいません、この場合もextern "C"でいけるんですね。
スレ汚し失礼しました。
25デフォルトの名無しさん:2008/07/17(木) 18:15:38
インテリジェントエージェントが動的コードスニペットでバグを起こしそうなコマンドや
構文にチェックをする。その段階でメタレベル構文にデバッグ情報が埋め込まれ、メモリリーク
や例外のときに情報がセットされる。
君が使うのはまだ難しいと思うよ。
怪しい変数をprintfで表示させるところから初めてはどうだろう?
26デフォルトの名無しさん:2008/07/17(木) 18:38:12
イミフ
27デフォルトの名無しさん:2008/07/17(木) 20:05:54
DEBUGでデバッグしたコードをRELEASEしたらクラッシュしてひどい目にあって以来
RELEASE以外でビルドしてない
出来上がるのは別のプログラムだからDEBUGでDEBUGしても何の意味もないよ
アホらしいけど
28デフォルトの名無しさん:2008/07/17(木) 20:11:50
>>27
直接関与はしてないけど
大学の研究室にそういうコードは存在した

なんかコード領域を実行時に書き換えてる風な挙動だった
初期化してないポインタでも使ってるような感じ

初代が作ったものを毎年手を入れていくものだから
何年目でそういうことになったのか不明
初代のコードはすっきりしてたのに、最新版は複雑怪奇w
29デフォルトの名無しさん:2008/07/17(木) 20:48:11
>>27
たまたまreleaseビルドで動いてるだけだったりしてな。
VSのバージョン上げてプロジェクト変換したら止まったり、
別のPCでexe動かしたら止まったりw
30デフォルトの名無しさん:2008/07/17(木) 21:03:00
Wallにしたらつらつらと出たりしてな。
31デフォルトの名無しさん:2008/07/17(木) 21:36:18
double hoge[100];

memset(hoge,0.0,sizeof(hoge));


これをするとdoubleからintへの変換っておこられるんですが、何がいけないんですか
32デフォルトの名無しさん:2008/07/17(木) 21:47:12
void* memset(void*, int, size_t)
33デフォルトの名無しさん:2008/07/17(木) 21:49:32
memsetはバイト単位でデータを埋めるのにしか使えない。
34デフォルトの名無しさん:2008/07/17(木) 21:58:58
double hoge[100] = {0.0};
これで全部0.0が入るんじゃね?
35デフォルトの名無しさん:2008/07/17(木) 22:13:30
>>31
第二パラメータを0にすればコンパイル自体はできますが、0.0で埋めたことになる保証はありません。
大人しく>34の手を使うかC++のstd::fill()を使うか自分でループを回しましょう。
3631:2008/07/17(木) 22:44:27
わかりました!どうも
37デフォルトの名無しさん:2008/07/17(木) 23:19:18
>>34
それ[0]は0.0だけど、[1]以降は0で埋めたことになるんじゃないか?
まぁ0.0も0も同じことだと思うけど
38デフォルトの名無しさん:2008/07/17(木) 23:23:45
子クラスにメンバ変数もデストラクタもない場合ときに、
public継承する場合は親クラスのデストラクタは
virtualにしないとまずい?

class Base
{
public:
  Base(int a, int b);
  ~Base();
private:
  int m_a;
  int m_b;
};

class A : public Base
{
public:
  A(int a);
};

これはまずい?
やりたいことは、
「親クラスのコンストラクタを制限したバージョン」
を作りたいんだが。
39デフォルトの名無しさん:2008/07/17(木) 23:26:03
何でコンストラクタから仮想関数を呼べるんですか?
どうせ誰も得しないんだろうからコンパイルエラーにしちゃえばいいのに。
40デフォルトの名無しさん:2008/07/17(木) 23:26:40
>>39
呼べるようにしたほうが設計的に美しいんじゃね?
41デフォルトの名無しさん:2008/07/17(木) 23:46:44
>>38
>「親クラスのコンストラクタを制限したバージョン」
>を作りたいんだが。

それの理由を書いた方が良いかと。
42デフォルトの名無しさん:2008/07/17(木) 23:53:25
WSAStartup(MAKEWORD(2,0), &wsd);
SOCKET sd = WSASocket(AF_INET, SOCK_STREAM, IPPROTO_TCP, NULL, 0, 0);
closesocket(sd);
WSACleanup();

それぞれ関数の後ろでGetProcessHandleCount()で
プロセスが開いているハンドル数を調べると、
WSASocket()で10個ハンドルが開き、closesocketしても減りません。

この10個のハンドルを閉じる方法はないんでしょうか?

WindowsXP Pro SP2、VisualStudio 2008 ExpressEditionです。

スレ違い?
43デフォルトの名無しさん:2008/07/17(木) 23:59:56
>>41
いや、これ自体に特に意味はないんだが。
環境依存のメモリリークとか発生しないかと思って。
44デフォルトの名無しさん:2008/07/18(金) 00:00:34
再利用するとかで内部的に完全には解放されてないだけじゃね?
WSACleanup()でも消えない?
45デフォルトの名無しさん:2008/07/18(金) 00:01:09
>>38
基底クラスのデストラクタを virtual にする必要があるのは、派生クラスの
インスタンスを基底クラスのポインタ経由で delete する場合。基底クラスの
デストラクタが virtual でないと、派生クラスのデストラクタが呼ばれない。
Base* b = new Derived();
...
delete b; // Derived::~Derived を呼ぶために、Base::~Base を virtual に!!!
RAII でインスタンスを破棄するなら、virtual である必要はない。
46デフォルトの名無しさん:2008/07/18(金) 00:02:02
>>42
WSASocket(); closesocket(); を交互に繰り返したら増えつづける?
47デフォルトの名無しさん:2008/07/18(金) 00:03:28
>>45
それはわかるんだが、
「子クラスにメンバ変数もデストラクタもない場合」
にどうなるのかってのが知りたかった。
4842:2008/07/18(金) 00:03:33
>>44
WSACleanup()の後でも減ってませんでした

>>46
会社にしか環境ないので
明日それをやってみます。
49デフォルトの名無しさん:2008/07/18(金) 00:06:32
>>48
ExpressEditionならタダで手に入る…
ってか会社でExpressEdition!
50デフォルトの名無しさん:2008/07/18(金) 00:10:50
>>38 >>47
Aからさらに継承しない限り問題無し
51デフォルトの名無しさん:2008/07/18(金) 00:15:40
>>49
会社でExpressEditionは別にいいだろ
商用利用可だし、IDEはともかくコンパイラが無料なのが重要なわけだから
52デフォルトの名無しさん:2008/07/18(金) 00:19:20
その無料のExpressEditionで数百万で売るもの作ってます^^
53デフォルトの名無しさん:2008/07/18(金) 00:21:11
>>38
それなら FactoryMethod でも使えば。
Base* CreateBase(int a);
5449:2008/07/18(金) 00:21:25
55デフォルトの名無しさん:2008/07/18(金) 00:23:00
gcc4.2でopenMP使ってforループ並列化しようとすると、
「ループカウンタがunsignedです」って警告される。

ループカウンタってsigned使うのが普通なの?
vectorとかsize_typeは大体unsignedだと思うんだけど。
56デフォルトの名無しさん:2008/07/18(金) 00:24:57
>>50
ありがと!
57デフォルトの名無しさん:2008/07/18(金) 00:35:03
>>55
実装上の都合だとでも思ってください。
0スタートのループを、逆条件にしても大丈夫なようにってことかもね。
58デフォルトの名無しさん:2008/07/18(金) 00:54:32
signedとunsignedの違いが問題になるような回数のループをやろうとすること自体に問題がある
59デフォルトの名無しさん:2008/07/18(金) 00:56:35
>>58
通常は size_type (unsigned) に合わせないとコンパイラが警告してくれちゃう
60デフォルトの名無しさん:2008/07/18(金) 00:57:51
まぁループはsignedにしといたほうが無難だろうね
61デフォルトの名無しさん:2008/07/18(金) 00:58:50
整数値を引数として与えその数値によって文字列を返す関数を作ったのですがうまくいきません
const char [2]' から 'charへの変換とかでます。どうしたらよいですか?

char abc(int number){

switch( number )
{
case 0:
return "A";
break;
case 1:
return "B";
break;

       ・
       ・
62デフォルトの名無しさん:2008/07/18(金) 01:03:12
"A" → 'A'
63デフォルトの名無しさん:2008/07/18(金) 01:04:50
2文字以上の場合もあるんですよ
64デフォルトの名無しさん:2008/07/18(金) 01:05:09
char* abc(int number){}
65デフォルトの名無しさん:2008/07/18(金) 01:05:53
まちがい
const char* abc(int number){}
66デフォルトの名無しさん:2008/07/18(金) 01:08:52
constがなぜいるんですか??
67デフォルトの名無しさん:2008/07/18(金) 01:22:43
文字列リテラルを書き換えてはイケナイ以上、
constを付けて防禦を計っておくべき、みたいな
68デフォルトの名無しさん:2008/07/18(金) 01:23:05
>>61
#include <stdio.h>
#include <stdlib.h>
char * abc(int number){
int rank = 1;
int num = number;
char *numarray;
while(num){
num /= 10;
rank++;
};
numarray = (char *)malloc(sizeof(char)*(rank+1));
sprintf(numarray,"%d",number);
return numarray;
}
int main()
{
char * ans = abc(123);
printf("%s \n",ans);
free(ans);
return 0;
}
69デフォルトの名無しさん:2008/07/18(金) 01:42:33
ループカウンタはsignedが普通って事は、
int size = static_cast<int>(instance_of_vector.size());
for (int i = 0; i < size; ++i) ...;
ってやればいいの?
70デフォルトの名無しさん:2008/07/18(金) 01:45:15
それだとINT_MAXを超えた値が返ってきたらsizeは-になるぞ。
いやまぁ2億を超える要素なんてないだろうけどw
71デフォルトの名無しさん:2008/07/18(金) 01:49:37
>>69
要はさ
for(unsigned int i = 10; i > 0; i -= 2)
みたいなことやっちゃったら無限ループになるから
ちゃんと解ってるならunsignedでも良いでしょう
72デフォルトの名無しさん:2008/07/18(金) 01:51:58
>>71
だから、OpenMPで警告が出るんだってばさ。
73デフォルトの名無しさん:2008/07/18(金) 02:05:28
理解してるなら警告は無視していい
74デフォルトの名無しさん:2008/07/18(金) 02:24:29
>>47
そんな条件は関係ない。デストラクタに virtual が付いてない基底クラスへのポインタが
実際には派生クラスを指している場合、 delete すると未定義動作になる。
75デフォルトの名無しさん:2008/07/18(金) 02:37:36
76デフォルトの名無しさん:2008/07/18(金) 03:24:25
virtualな関数が増えると、ポリモーフのコストって増える?
77デフォルトの名無しさん:2008/07/18(金) 04:49:34
GNUのライブラリを使って、ソフトやライブラリを作ったら
元のGNUのソースを同封しないといけませんか??
78デフォルトの名無しさん:2008/07/18(金) 04:52:32
元のソースに手を加える改良の場合は変更後のソースを入れないと駄目なんですよね
改変せず利用するだけならば、入れなくて良いですか?
GNUのライブラリを使用していると明記する必要ありますか?
79デフォルトの名無しさん:2008/07/18(金) 05:03:49
>>77-78 ライセンス嫁。あと GPL なら GPL FAQ 日本語訳とか。
80デフォルトの名無しさん:2008/07/18(金) 05:25:33
GNUのコード使ったら、
81デフォルトの名無しさん:2008/07/18(金) 05:29:24
GNUを利用したら、改変のある無しに関わらず、ソースコードもうpせよ
ってことでOK?
具体的には、GNUコードから、WindowsのスタティックリンクかDLLを作って
それを自分のソフトで使用した場合は、自分のプログラムのコードをうpするって事?
82デフォルトの名無しさん:2008/07/18(金) 08:47:02
初心者質問てここでいいのですかね?
もしスレ違いなら誘導お願いします。
private継承について質問なのですが、親から継承したメンバはすべてprivateになり
子クラスからアクセスできないものと思っておりますが、違うのでしょうか。
実際コードを書いて確認してみたところ、アクセスできないぽいのですが
サイトによってアクセスは可能と書いているところもあるので混乱しています。
アクセスする方法があれば教えていただきたいです。
それと、private継承を調べると「実装の継承」という言葉がたいてい出てくるのですが、
これの意味がよくわかりません。
「実装の継承」の実際の使い方など教えていただけませんか。
83デフォルトの名無しさん:2008/07/18(金) 09:06:13
書物はまだしも、サイトの記事なんて鵜呑みにする方がどうかしている。
84デフォルトの名無しさん:2008/07/18(金) 09:24:31
getHoge(),setHoge()のような関数(アクセサ)を継承元で書かないとアクセスできないよ。

private継承、実装の継承というのは、基底クラスで定義された関数など「実装」のみを継承し、
インターフェイスや性格については基底クラスと同じものを持たなくて良い
=基底クラスのオブジェクトではあれができたから継承先でも出来るだろうという期待が出来ない継承のことかな。
逆にpublic継承というのは、DerivedクラスはBaseクラスの一種であるとみなして操作できなければならなくて、
BaseがCry()と言う関数を持ってたらDerivedも持っていなくてはいけないし(鳴き声は違うにしても)同じような動作をしなくてはいけない。

…という話がEffective C++に詳しく書いてあるので読んでおこう。
85デフォルトの名無しさん:2008/07/18(金) 10:02:33
>>77,78
LGPLかGPLで扱いが変わって来るはず。
glibcとリンクしただけで全てのプログラムが公開されなければいけないなら、
Unix系で商用ソフトなんて作れなくなるよ。

>>81
再配布条件と利用条件は区別して考えてる?
作ったプログラムを公開しないのであれば、何もUPする必要は無いよ。
86デフォルトの名無しさん:2008/07/18(金) 10:06:58
>>83
鵜呑みしないで疑っているからここにいるわけで
87デフォルトの名無しさん:2008/07/18(金) 16:33:35
[1] 授業単元: プログラミング
[2] 問題文(含コード&リンク):

配列の要素を昇順にソートしたときの、添え字の順番を配列に記憶するプログラムを書け。

data = {2,6,3,1,2} なら, index = {3,0,4,2,1}である。

元の配列は書き換えてはならない。

qsortなどのライブラリを用いて構わない。

[3] 環境
 [3.1] OS: Windows
 [3.2] コンパイラ名とバージョン: gcc
 [3.3] 言語: C C++
[4] 期限: 明日
88デフォルトの名無しさん:2008/07/18(金) 16:52:11
誤爆しました・・・
89デフォルトの名無しさん:2008/07/18(金) 18:11:05
そいじゃ、誤爆で
int [] data = { 2, 6, 3, 1, 2 };
int [] index = data.Select((a, i) => new { a, i }).OrderBy(x => x.a).Select(x => x.i).ToArray();
90デフォルトの名無しさん:2008/07/18(金) 20:53:48
>>84
回答ありがとうございます
実装への直接的なアクセスをできないようにすることで
実装については変更させず、他の部分のみ変更可能にする
ということなのですかね
Effective C++も探して読んでみます
91デフォルトの名無しさん:2008/07/18(金) 21:44:50
>>71
だなあ。
結局unsignedのメリットって1bit表現範囲が広がるくらい?
92デフォルトの名無しさん:2008/07/18(金) 21:59:32
unsignedだとオーバーフローで鼻からなんか発生しない。
93デフォルトの名無しさん:2008/07/18(金) 22:25:54
>>91
signedな整数は符号拡張がウザいこともあるし
ビット演算や何かとの相性も良くない

まあ、適材適所で使い分けろ
94デフォルトの名無しさん:2008/07/19(土) 00:40:43
>>92
鼻から牛乳がオーバーフローしました
95デフォルトの名無しさん:2008/07/19(土) 15:30:21
>>91
境界チェックの比較が1回で済む
96デフォルトの名無しさん:2008/07/19(土) 17:14:33
いつ誰がsignedに書き換えるかわからないんだからそこはちゃんと比較しとけよ
本当にunsignedなら最適化してくれる
97デフォルトの名無しさん:2008/07/19(土) 17:16:03
そうですよね
いつ誰が構造体に書き換えるかわからないですもんね
98デフォルトの名無しさん:2008/07/19(土) 19:10:21
なんでこれで
while( *d++ = *s++ )
文字列コピーできるんですか?
99デフォルトの名無しさん:2008/07/19(土) 19:17:41
>>98 なんでコピーできないと思うの?
100デフォルトの名無しさん:2008/07/19(土) 19:19:20
while(( *d++ = *s++) != 0)
101デフォルトの名無しさん:2008/07/19(土) 19:37:45
演算子の優先度が分からないのか、ポインタのインクリメントの意味が分からないのか
102デフォルトの名無しさん:2008/07/19(土) 20:21:47
std::vector<CTest> hoge;
void testFunc()
{
for(int i=0; i<10;i++){
CTest test;
test.i = i;
hoge.push_back(test);
}
}

int main(){
testFunc();
for(int i=0; i<hoge.size();i++){ printf("%d\n",hoge[i].i);
}
こんなことしても問題ありませんか?一応表示はされたのですが。
std::vector<int>とかはそのまま数値いれてますけど、
std::vector<クラス>の時もnewしないで入れても平気なのかなって思いまして。
103デフォルトの名無しさん:2008/07/19(土) 20:28:05
CTestの実装による

push_back内でnewしてコピーしてるのでnewはいらない
で、そのコピーのときにCTestのコピーコンストラクタでメンバのコピーがされる

デフォルトコピーコンストラクタでも問題ないなら特にコーディングしてなくてもおk
デフォルトコピーコンストラクタじゃだめなら自分で書く必要あり
104デフォルトの名無しさん:2008/07/19(土) 20:38:08
なるほど。ありがとうございました。
105デフォルトの名無しさん:2008/07/19(土) 21:04:33
Cを書いてるとエディターの機能で色分けしてくれて表示
されるのは便利なのですが、さらに進んで
ある行にカーソルを置くとどういう階層のとこに
いるかって機能がついたエディタとかってありますか?

main()
{
if(a==1)
{
while(b>1)
{

 if(c==0)
{
ここ
}
}
}
}

「ここ」にカーソルを置くと
main()->if(b==1)->while(b>1)->if(c==0)

みたいに表示されるやつ
106デフォルトの名無しさん:2008/07/19(土) 23:33:41
それを見たくなるってのは、もしかして、
1つの関数に詰め込みすぎのサインだったりするんじゃないかな。
107デフォルトの名無しさん:2008/07/19(土) 23:39:33
「そういうコードは書かない方がいい」じゃだめですか
108デフォルトの名無しさん:2008/07/19(土) 23:52:23
関数の形でかかれているものを問答無用でインラインに展開する方法があればいいな、と思うのですが。
109デフォルトの名無しさん:2008/07/19(土) 23:53:22
VCにそんなオプション有った気が
110デフォルトの名無しさん:2008/07/19(土) 23:53:26
>>108
思うだけにしておいたほうがいいと思います
111デフォルトの名無しさん:2008/07/20(日) 00:06:57
>>108
闇雲にインライン展開しても速くならないんだな。
112デフォルトの名無しさん:2008/07/20(日) 00:09:33
>>105
1画面に収まらない関数は書かないのが鉄則ですう
113デフォルトの名無しさん:2008/07/20(日) 01:01:24
そんなこといっても行数が増えてくると
関数呼び出しだけでも一画面におさまんなくなって
便利な機能な気がするけど…
ウィンドウプロシージャとかでかい関数はどうしてもできるわ(´・ω・`)
一つのファイルにいっぱい関数詰め込むととか
あとアルゴリズムを激しく書く人はいる気がする。
何千行ものコードを一画面に収まるくらいに
分けたら関数出来過ぎ君だわ

なんかおれ必死な感じだけど、便利な気がするけど…
ないってことは作るしかないんかな。
114デフォルトの名無しさん:2008/07/20(日) 01:04:08
ウィンドウプロシージャをCで書くならメッセージクラッカ必須だろ。
115デフォルトの名無しさん:2008/07/20(日) 01:06:06
>>108
inlineじゃだめですか?
116デフォルトの名無しさん:2008/07/20(日) 01:27:26
>ウィンドウプロシージャとかでかい関数はどうしてもできるわ
出来ねぇよ、関数分けろ
117デフォルトの名無しさん:2008/07/20(日) 01:30:33
ファイルで分割しても二桁とか
118デフォルトの名無しさん:2008/07/20(日) 01:42:52
>>713
OK,読み間違えてた
ダイビング土下座しながら吊ってくる
119デフォルトの名無しさん:2008/07/20(日) 01:43:24
誤爆
120デフォルトの名無しさん:2008/07/20(日) 02:42:46
>>115
inlineにしててもインライン展開しないこともあるんだったよな確か?
121デフォルトの名無しさん:2008/07/20(日) 02:50:40
なるべく最新版のやつで最適化するしかないよ
マクロにすれば確実にインラインになるけど、デバッグが困る
122デフォルトの名無しさん:2008/07/20(日) 02:53:58
>>120
inlineにしなくてもインライン展開されることもあるしね。
123デフォルトの名無しさん:2008/07/20(日) 03:01:41
クラッカ使ってないな
そういうのあるんだ
古い人だから#defineとか
いっぱい使うとわかんなくなるから
カーニハンとリッチーだっけ?
あれの本だとcはシンプルで
なんとかってのってたけど
いいねそれ。
ただ今の時代では違うのかもだけど。

とりあえず今1万7千行くらい
switchcase文がいっぱいあるわ。
c標準のデータ型以外は
最低限のやつしかwindows.h系のは
使ってない。

でも昔よりは関数で分けるようになったかも
124デフォルトの名無しさん:2008/07/20(日) 03:31:34
>分けたら関数出来過ぎ君だわ
それくらいがむしろ普通
125デフォルトの名無しさん:2008/07/20(日) 03:51:00
ウィンドウプロシージャには
関数分けするためのマクロが用意されているくらいなのにな。
126デフォルトの名無しさん:2008/07/20(日) 05:22:05
VCでマルチバイトというとUTF-8、UNICODEというUTF-16ですよね?
SJISで作ったテキストファイルも普通に読み込んでいると思うのですが何故でしょう?
127デフォルトの名無しさん:2008/07/20(日) 05:30:13
マルチバイトというと(一般的な日本語Windows環境では)CP932だと思うが。
128デフォルトの名無しさん:2008/07/20(日) 05:42:54
CP932、ググるSJISの拡張ということで互換性あるのかな
どうもUTF-8だと思ってたのは勘違いのようですね
文字コードってユーザーとして意識したことないから難しい...
129デフォルトの名無しさん:2008/07/20(日) 08:55:06
>>112
そんな鉄則ねえよ。
130デフォルトの名無しさん:2008/07/20(日) 12:25:29
あるよ。井戸の外には
131デフォルトの名無しさん:2008/07/20(日) 12:30:20
「愚かな一貫性は小人物に憑いたおばけである」
という言葉があってのう
132デフォルトの名無しさん:2008/07/20(日) 13:45:18
1画面なんて言われたら、250桁×100行でも許容しろってことかよ。

冗談じゃねぇ。
133デフォルトの名無しさん:2008/07/20(日) 13:49:48
分かり易ければ1画面に収まる必要まったくなし
こだわってるやつはたいてい頭悪い
134デフォルトの名無しさん:2008/07/20(日) 13:54:50
>>132
1600x1200?w
寧ろ、3分割して80桁x300行とか嫌そうだw
135デフォルトの名無しさん:2008/07/20(日) 13:56:38
A4一枚とかはよく見聞きする話
136デフォルトの名無しさん:2008/07/20(日) 14:06:39
明日から7ptフォントで開発しとけよ。
137デフォルトの名無しさん:2008/07/20(日) 14:10:04
初心者には一画面以内 must で教える
上達したら一画面越えてもいいよと教える
138デフォルトの名無しさん:2008/07/20(日) 14:14:15
マクロで質問です。

#pragma message("hogehoge") をマクロにしたいんですが...

次のやり方でコンパイラが怒ります...。

#define _message( str ) #pragma message( str )

どう登録すれば良いんでしょうか?
139デフォルトの名無しさん:2008/07/20(日) 14:22:41
プラグマをマクロにした例はみたことないなぁ
できないんじゃないの?
140デフォルトの名無しさん:2008/07/20(日) 14:24:27
できないよ。
141デフォルトの名無しさん:2008/07/20(日) 14:53:05
だからC99で_Pragmaが追加された。
VC++も2008から__pragmaという名称で同じ機能を用意している。
142デフォルトの名無しさん:2008/07/20(日) 15:17:57
プラグマをマクロ化って。
誰が得するんだ…。
143デフォルトの名無しさん:2008/07/20(日) 15:22:58
>>142
処理系によってプラグマの書き方が異なる場合
144デフォルトの名無しさん:2008/07/20(日) 15:37:54
>>143
いや理論的にはそんなんだけど、俺の未熟な経験からは
使った方が便利だってケースが思い当たらない。
そんで誰が得するのかな、と。
145デフォルトの名無しさん:2008/07/20(日) 16:06:04
>>144
処理系A #pragma align packed
処理系B #pragma pack(1)
だとすると、構造体の定義のたびに、

#if defined(_IMPL_A)
#pragma align packed
#elif defined(_IMPL_B)
#pragma pack(1)
#endif
struct S {...}
#if...さらにアライメントを元に戻すpragma

と書かないといけない。

さらに処理系C #pragma options align=packed
を追加したくなったら、もううんざりだ。
146デフォルトの名無しさん:2008/07/20(日) 16:14:15
includeでやるのはどう?
147デフォルトの名無しさん:2008/07/20(日) 16:17:04
>>146
うん。実際そうやってた。
でも美しくないんだよねえ。構文的に
148デフォルトの名無しさん:2008/07/20(日) 16:39:11
>>130
井戸の中にしかないと思われ。
149デフォルトの名無しさん:2008/07/20(日) 17:16:25
VC++2005EEで作成しています。
有る関数の中でループを毎に乱数を発生させ、配列に値を保存させようとしたのですが
実行画面では同じ数値に成ってしまいました。デバックをしてみたところ

@1から見ていくと、配列にちゃんと違う数値が入っていき、ループを抜けた
@2までみても違う数値が保存されていました。

@2にブレークポイントを設定し、そこで値を確かめるとListの値には
同じ数値が配列に保存されていました。

全て値がう値が保存されている様にしたいのですが、何が問題になっているのか見当がつきません。
何か対策とかあるのでしょうか

srand( (Uint32)time(NULL) );
m_Tmp = new Object();
@1
for ( Uint32 i=0; i<MAX; ++i )
{
m_List.push_back( *m_Tmp );
m_List[i].SetNum( rand() % 10 );
}
@2
※SetNumは与えられた値を保存させるだけのメソッドです。
150デフォルトの名無しさん:2008/07/20(日) 17:19:22
STLのstd::vector<int>とか使ったらいいとおもうよ。
151デフォルトの名無しさん:2008/07/20(日) 17:22:06
m_Listは std::vector<Object> m_List;で宣言してあります。
152デフォルトの名無しさん:2008/07/20(日) 17:26:02
Object()のコピーコンストラクタとか、どっか実装がおかしいんじゃね?
153デフォルトの名無しさん:2008/07/20(日) 17:27:51
>>149
ちょwww
これはだめでしょ
Object は最初に1回 new しただけでしょ?
そこに値をどんどん入れて行ったら、当然同じインスタンスに値をどんどん突っ込むわけで、
最後には、一番最後に代入した値ばっかりのリストになるよwww
154デフォルトの名無しさん:2008/07/20(日) 17:28:56
>>149
Object の定義が怪しい。 SetNum の値をポインタの先に保存してて、 Object のコピーでは
ポインタがコピーされてるとか。

>>153 push_back(*m_Temp) だから、そこが問題じゃないでしょ。
155デフォルトの名無しさん:2008/07/20(日) 17:29:38
済みません。事故解決しました。
SetNumで違う変数に値を保存してました。お騒がせしました orz
156149:2008/07/20(日) 17:30:23
そっか、push_back でコピ^コンストラクタが動くのか、
じゃあ152が正しいか。
157デフォルトの名無しさん:2008/07/20(日) 22:22:03
現在自作ゲームで文字の時間差表示をしようとしているのですが、
string script="abcde";
string strbuf="";
int moji=0;

for(int i=0;i<script.size();i++){
strbuf+=script[moji];
//ここでstrbufの内容を表示
//ここにwait処理が入る
moji++;
}

strbuf="";
moji=0;

scriptの中身が1バイト文字だと正常に表示されるんですが、
2バイト文字だと文字の背後に・(黒点?)が表示されてしまいます
stringは2バイト文字は使えないんでしょうか?
158デフォルトの名無しさん:2008/07/20(日) 22:23:27
wstringとか
159デフォルトの名無しさん:2008/07/20(日) 22:32:17
マルチバイト文字列用のルーチン使って文字を切り出すか、UTF-16をつかう。

おそらくstd::stringで1バイトづつ出力させてるんだろうけど、それやっちゃうと2バイト文字は半分ちぎれたりするから正常に表示できない。
ちゃんと2バイト文字は2バイトづつ出力させるか、2バイト固定のUTF-16使えばOK。
荒技としては逆に1バイト文字を使わないという手もある。(全角数字、全角アルファベット、全角記号で代用)
160デフォルトの名無しさん:2008/07/20(日) 22:35:47
なるほど、要はscript[moji*2]とかループを1/2回にするなり
数字は全角で書くなりすれば良いわけですね
ありがとうございます
161デフォルトの名無しさん:2008/07/20(日) 22:44:30
>>159
UTF-16だから2バイト固定なんてことが許される時代はもう終わっているよ。
162デフォルトの名無しさん:2008/07/20(日) 22:47:14
サロゲートなんて捨ててOK
163デフォルトの名無しさん:2008/07/20(日) 22:52:10
C/C++って、マルチバイト文字の、先頭か二番目以降かって判定する関数なかったっけ?
標準でなくても、それぞれのプラットホームには必ずあると思うけど。
164デフォルトの名無しさん:2008/07/20(日) 22:52:40
[゛], [゜] も捨ててかまわないってことで。
165デフォルトの名無しさん:2008/07/20(日) 22:57:08
>>162
つUTF-8, UTF-32
166デフォルトの名無しさん:2008/07/20(日) 22:59:55
>>163
そんなレガシー技術に頼るぐらいならUnicodeにしとけよ

UTF-8では先頭バイトと後続バイトはMSB側の2bitを見るだけで簡単に区別できるし
先頭バイトだけで後続バイト数は判断できるし
後続バイトがASCII文字と重なるようなこともない

マルチバイト処理は必要だが、レガシーなエンコーディングスキームよりは
ずっといい性質を持っている
167デフォルトの名無しさん:2008/07/20(日) 23:00:00
>>165
つwchar_t
168166:2008/07/20(日) 23:04:30
補足。
euc-jpやiso2022系では、「lead byteかどうか」は特定の2バイトを見ただけでは
判断できない。
行頭なり何なりから順番に舐めるしかないはずだよ。

>>163の言っているような"iskanji"風のレガシーなクソマクロは、特定の条件でしか
役に立たないものだ。
169デフォルトの名無しさん:2008/07/20(日) 23:09:52
>>168
先頭から見ないとわからないってのは、EUCのほうじゃなくてShift JISのほうでは?
170デフォルトの名無しさん:2008/07/20(日) 23:15:37
なんで文字コードごときの話でそんな偉そうにできるんですか?
171デフォルトの名無しさん:2008/07/20(日) 23:18:27
>>170
皆、思い思いに書いてるだけだよ。
偉そうに見えるのはおそらく・・・
172デフォルトの名無しさん:2008/07/20(日) 23:23:01
>>169
EUCで簡単なのは1byteコードと2byteのコードの識別だけで、
lead byteとtrail byteの識別は難しいのでは?
173デフォルトの名無しさん:2008/07/20(日) 23:31:16
入出力(ファイル、パイプ)はともかく、
内部コードにUTF-8, UCS2, UTF-16, UTF-32以外を使うのは止めておけ。
マジで。
174デフォルトの名無しさん:2008/07/20(日) 23:40:52
wchar_tはC/C++の定義上1文字なので、
固定サイズであるUCS2/UTF-32と考えるのはそれほど問題でないが、
可変サイズであるUTF-8/UTF-16として扱うのは完全にNG
175デフォルトの名無しさん:2008/07/20(日) 23:43:05
VC++で、ソースコードをUTF-8で保存してコンパイルしたら、"文字列" がUTF-8になってくれればいいんだけどね
176デフォルトの名無しさん:2008/07/20(日) 23:50:50
VC++(UCS2)/gcc(UTF-32)での可搬性を考えると、
wchar_t=UCS2と想定するのが良い

UTF-16、UTF-32はC++0xが出てくるまで我慢
177176:2008/07/20(日) 23:53:11
もちろん、ICUなどで提供されている型や関数を使っている人は除く
178デフォルトの名無しさん:2008/07/21(月) 02:42:01
どーでもいいよそんなの
179デフォルトの名無しさん:2008/07/21(月) 08:10:43
>>175
C++0xでUTF-8リテラルが追加される。u8"文字列"

※ime.nu通すと#以降が消えるので
ttp://ja.wikipedia.org/wiki/C%2B%2B0x#.E6.96.B0.E3.81.9F.E3.81.AA.E6.96.87.E5.AD.97.E5.88.97.E3.83.AA.E3.83.86.E3.83.A9.E3.83.AB
180デフォルトの名無しさん:2008/07/21(月) 14:04:39
printf("aaa\b\b\b");

とかやってるコードを見かけたのですが、
\b\b\bはどういう意図でやっているのでしょうか?
\bはバックスペースのようですが…
181デフォルトの名無しさん:2008/07/21(月) 14:20:49
次に書いた文字がaaaを上書きする。
182180:2008/07/21(月) 14:40:00
>>181さんありがとうございます。

ファイルコピーの進捗状態をコンソール上の同じ位置で
パーセント表示する際などに
使うわけですね。なるほど。
183デフォルトの名無しさん:2008/07/21(月) 19:36:23
char *p;
char **pp = malloc(sizeof(char*) * 100);

という式はcharのポインタのポインタを100確保したという意味でいいのですか?
pp[0]はpと同じ意味ですか?
184デフォルトの名無しさん:2008/07/21(月) 19:42:56
char*を100個格納できるエリアへのポインタを返していて、そのポインタをppに入れている
あくまでも指定されたサイズのエリアを確保しているだけで、ポインタを確保している訳ではありません。

上記コード上ではpとpp[0]には何の関連もないけど、
p = pp[0];ができる?という意味なら、できる。
185デフォルトの名無しさん:2008/07/21(月) 22:34:01
>>184
同じ意味とは型が同じかという意味でした。
186デフォルトの名無しさん:2008/07/21(月) 23:08:32
VCで作ってタソーすをgccでコンパイルしようとすると
tchar.hがないってエラーになるんだが、
Linuxでは何てヘッダを読み込めば_TCHARとか_T()とか使える?
自分で定義するしかない?
187デフォルトの名無しさん:2008/07/21(月) 23:17:41
当たり前だ
188デフォルトの名無しさん:2008/07/22(火) 04:22:32
そのための_TCHARだ。
189デフォルトの名無しさん:2008/07/22(火) 04:24:17
gcc だと何と定義すりゃいいんだろうな。
wchar_t が UCS4 だったりすることもあるんじゃないのか。
190デフォルトの名無しさん:2008/07/22(火) 14:21:02
そもそもAPIにAとWの区別もないのに何の意味があるんだろう。
191デフォルトの名無しさん:2008/07/22(火) 14:28:47
>>190
WしかないAPIもある
192デフォルトの名無しさん:2008/07/22(火) 14:34:56
>>191
そんな話はしていない
193デフォルトの名無しさん:2008/07/22(火) 16:50:58
>>189
UCS2でも4でも動くように書くしかないかと
あるいはライブラリを使うか
194デフォルトの名無しさん:2008/07/22(火) 17:33:55
wchar_tの中身がUnicode系ではない環境もあるのでよろぴこ。
195デフォルトの名無しさん:2008/07/22(火) 20:54:18
>>194
その処理系の名前教えて。
いや、煽りとかじゃなくて普通に知りたいので。
196デフォルトの名無しさん:2008/07/22(火) 21:25:07
>>195
Linux以外のほぼすべてのUNIX。
すくなくとも、Solaris FreeBSD NetBSDはUnicodeではなかったはず。


197デフォルトの名無しさん:2008/07/22(火) 22:00:16
そうなのか。dクス
198デフォルトの名無しさん:2008/07/22(火) 22:02:46
LinuxをUNIXと言うと基地外が来襲するので
ちゃんとUNIXライクOSと言いましょう
199デフォルトの名無しさん:2008/07/22(火) 22:11:08
wchar_tマジ使えなさすぎワロタ
http://ml.tietew.jp/cppll/cppll/article/862
200デフォルトの名無しさん:2008/07/22(火) 22:40:13
その辺に載ってる話はさすがに古くねえか?
gcc 2.xだろ?
201デフォルトの名無しさん:2008/07/22(火) 22:55:17
gccのwchar_tは昔からうんこ
あまりにも有名すぎる話
202デフォルトの名無しさん:2008/07/22(火) 23:37:26
>>201
いやその、今のgccはinput-charsetだのexec-charsetだのwide-exec-charsetだの
指定できるだろ?
203デフォルトの名無しさん:2008/07/23(水) 01:49:03

*i |= 3;

はちゃんと

*i = *i | 3;

に展開されるのでしょうか?
204デフォルトの名無しさん:2008/07/23(水) 02:26:54
いいえ、前者と後者では意味が違います。
205デフォルトの名無しさん:2008/07/23(水) 02:32:22
>>203
「展開される」の意味が分からない

Cだと結果は動作は等しくなる
C++だとoperatorのオーバーロードがあるのでなんともいえない
206デフォルトの名無しさん:2008/07/23(水) 10:02:00
class test {
string* p;
public:
test() { p = new string; }
~test() { delete p;}
}

main() {
test obj1;
test obj2 = obj1;
}

2度目のdeleteにてセグメンテーション違反で落ちるコードです
教科書ではコピーコンストラクタを上書きして
ポインタの指す先までコピーするようにしてるのですが
delete時にチェックする方法はあるんでしょうか?
実用性は考えていませんが、興味があります

環境:
Linux kernel 2.6-686
GNU C++ compiler 4.1.1
207デフォルトの名無しさん:2008/07/23(水) 10:07:15
ローカル変数とは定義された順にスタックに積まれるのですか?
208デフォルトの名無しさん:2008/07/23(水) 10:13:42
>>206
obj2.pはobj1.pと同じだから落ちて当たり前。
何がしたいのか分からないけど、ポインタにNULLポインタを入れておけば
それがdeleteされても問題なく動く。
209デフォルトの名無しさん:2008/07/23(水) 10:13:50
>>206
> delete時にチェックする方法はあるんでしょうか?

参照カウンタをどこかに持つとか。

210デフォルトの名無しさん:2008/07/23(水) 10:18:20
あー、参照カウンタにしても、けっきょくコピーコンストラクタをオー
バーライドしなきゃいけないか。



211デフォルトの名無しさん:2008/07/23(水) 10:25:16
>>208
どこでNULLをセットすればいいですか?

>>209
なるべく簡単な方法がいいんですよね

catchしちゃえばいいのかな
このアドレスは使っちゃ駄目みたいなのは
カーネルに聞けば教えてくれるのかなと思ったんですが
212デフォルトの名無しさん:2008/07/23(水) 10:33:33
>>206
あくまでチェックしたいってことなら、方法は無い。
ヌルをセットするとかして、とにかく落ちないようにするなら auto_ptr でも使っとくのが簡単。

#include <memory>
#include <string>
using std::string;
using std::auto_ptr;

class test {
auto_ptr<string> p;
public:
test() : p(new string) {}
};

int main() {
test obj1;
test obj2 = obj1;
}
213デフォルトの名無しさん:2008/07/23(水) 11:37:38
>>207
規格ではスタックが使われるのかすら決まってなかった気がする
214デフォルトの名無しさん:2008/07/23(水) 12:39:32
>>211
string*ではなくstringをメンバに持たせる
215デフォルトの名無しさん:2008/07/23(水) 16:25:27
class hoge{
private:
int fuga;
public:
void setfuga(int a){ fuga = a; }
int getfuga(){ return fuga; }
};

class foo{
private:
std::vector<hoge> var;
public:
void sethoge(hoge hage){ var.push_back(hage); }
std::vector<hoge> getvar(){ return var; }
};

int main(){
foo foo0;
hoge hoge0;
hoge0.setfuga(1);
foo0.sethoge(hoge0);

std::vector<hoge>::iterator itr;
itr = foo0.getvar().begin();
std::cout << foo0.getvar().at(0).getfuga() << std::endl;
std::cout << (*itr).getfuga();
return 0;
}
これを実行すると、一つ目のcoutは正常に出力(1)されますが、二つ目はでたらめな値が出ます。
itr = foo0.getvar().begin()はfoo0.getvar().at(0)を指すiteratorだと思うので、同じ結果になると
思っているのですが…。どなたかお教えいただけると助かります。
216デフォルトの名無しさん:2008/07/23(水) 16:35:26
>itr = foo0.getvar().begin();

getvarの戻り値はfoo0.varそのものではなくfoo0.varの一時的なコピーで、次の文に移る前には破棄される
getvarはfoo0.varのコピーを返すのではなくfoo0.varへの参照を返す必要がある
217デフォルトの名無しさん:2008/07/23(水) 16:38:55
>>216
その通りでした。ちょうど思いついたところでした。
すみません、どうもありがとうございます。
218デフォルトの名無しさん:2008/07/23(水) 20:39:07
HOGEという構造体がtypedefされているとします。


HOGE *hoge;と宣言します。


void function(HOGE *hoge){

}という関数に

function(hoge)と渡すと参照渡しになってますか?
219デフォルトの名無しさん:2008/07/23(水) 20:42:42
>>218
それはC++でいうところの参照ではありません
220デフォルトの名無しさん:2008/07/23(水) 20:44:26
アドレス私ですか?
221デフォルトの名無しさん:2008/07/23(水) 20:46:44
222デフォルトの名無しさん:2008/07/23(水) 20:47:38
アドレス渡しですか?の間違いです
223デフォルトの名無しさん:2008/07/23(水) 21:01:10
「自分宛のレスですか?」という意味だと勘違いしたのは、
俺だけじゃないはず。
224デフォルトの名無しさん:2008/07/23(水) 21:33:45
foo(HOGE fuga){ }
bar(HOGE* pFuga){ }
baz(HOGE& fuga){ }

func()
{
HOGE hoge;
HOGE *pHoge;

// 値渡し
foo(hoge);
// ポインタ渡し(アドレス渡し)
bar(pHoge);
// 参照渡し
baz(hoge);
}
225デフォルトの名無しさん:2008/07/23(水) 21:40:34
foo(HOGE fuga)
foo(HOGE &fuga)

HOGE hoge;
foo(hoge);

この場合どっちが優先されますか?
226デフォルトの名無しさん:2008/07/23(水) 21:43:00
>>225
自分でコンパイルしてみては?
227デフォルトの名無しさん:2008/07/23(水) 21:44:40
自分で試してください。

俺は試しました。VC++2005EE

XXX.cpp(19) : error C2668: 'foo' : オーバーロード関数の呼び出しを解決することができません。(新機能 ; ヘルプを参照)
XXX.cpp(11): 'void foo(HOGE &)' の可能性があります。
XXX.cpp(7): または 'void foo(HOGE)'
引数リスト '(HOGE)' を一致させようとしているとき
228デフォルトの名無しさん:2008/07/23(水) 21:44:44
もし環境依存だったら自分で試しただけでは分からないし
229デフォルトの名無しさん:2008/07/23(水) 21:50:02
それは試してうまくいった後に質問すべきこと。
230デフォルトの名無しさん:2008/07/23(水) 22:08:24
g++でプリコンパイル済みヘッダが使えないって聞いたんだが、
stdafx.hみたいに一つのヘッダファイルでSTLやboostとかのヘッダ
全部読み込むのはやめたほうがいい?
231デフォルトの名無しさん:2008/07/23(水) 22:44:37
いつのg++の話?
232デフォルトの名無しさん:2008/07/23(水) 23:54:09
>>224
225は自分じゃないです。

ポインタ渡しした場合はbar関数の中で値を書き換えても、元には影響ないんですか?
233デフォルトの名無しさん:2008/07/24(木) 00:03:05
>>232
ポインタを引数に指定しないとだめか、そうでないかの違いで、影響あることには変わりないよ
234デフォルトの名無しさん:2008/07/24(木) 00:10:51
225は違う人だったのか…

ポインタ渡しは影響する
参照渡しも影響する
値渡しだけは影響しない
235デフォルトの名無しさん:2008/07/24(木) 00:21:32
クラスは参照型なのでゴニョゴニョ
236デフォルトの名無しさん:2008/07/24(木) 00:23:12
>>232
bar(HOGE* pFuga){
  *pFuga = ...; //影響する
  pFuga = ...; //影響しない
}
237デフォルトの名無しさん:2008/07/24(木) 02:02:44
>>230
そういう理由もあるだろうし、依存関係は最小限にしたほうがいいと思うよ。

g++ でもプリコンパイル済みヘッダ自体は使えたような気がする。使い方が
全然違ったはずだけど。
238デフォルトの名無しさん:2008/07/24(木) 09:04:36
>>235
嘘をつくな
239デフォルトの名無しさん:2008/07/24(木) 13:36:21
あれ?
クラスもコピーコンストラクタ呼ばれて値渡しされるよね?
240デフォルトの名無しさん:2008/07/24(木) 13:39:58
コピーコンストラクタ呼ばれて値渡しされるし、逆にコピーコンストラクタが定義されていないと
コンパイルできないはず
241240:2008/07/24(木) 13:42:25
値渡しの話だよね?
242デフォルトの名無しさん:2008/07/24(木) 13:43:59
コピーコンストラクタがなければ勝手に丸ごとコピーします。
でないと、struct A a, b; a = b;というC由来のコードがコンパイルできなくなってしまう。
243240:2008/07/24(木) 13:44:40
あ、そっか、そうだね、失礼
244240:2008/07/24(木) 13:47:05
あ、よくがんがえたら、クラスのメンバーに、コピーコンストラクタが定義されていないオブジェクトが含まれている時と
勘違いしてた。
自分がよくコンパイルエラー出すもんで。。w
245デフォルトの名無しさん:2008/07/24(木) 13:52:09
実際
中間インスタンス生成+コピーコンストラクタ呼んだ後は 参照でわたしてる?

呼び出し元のインスタンスには影響を与えないけど、スタックに実体を積んでいるわけではない
みたいな構造
246デフォルトの名無しさん:2008/07/24(木) 13:53:44
それぞれ想定している状況が違っている悪寒。
247デフォルトの名無しさん:2008/07/24(木) 13:55:27
VC2008 VC6 BCC MinGW
でboostいれたいんですけど
バイナリ配布しているVC2008しか成功しません
1.35のそれぞれのバイナリ置いてある所無いですか?
248デフォルトの名無しさん:2008/07/24(木) 14:17:41
http://www.boost.org/development/tests/release-1_35_0/developer/summary.html

boostてdrwinとvc7以上で主に動くんですね borlandはかなり駄目ですね
249デフォルトの名無しさん:2008/07/24(木) 14:39:09
darwinってmacのことだぞ
250デフォルトの名無しさん:2008/07/24(木) 19:59:10

 boost::regex で,置換する時に置換フォーマットが $10 だと 10 番目のキャプチャ要素に置換されるんだけれど,
これを一番目のキャプチャ要素 $1 + 0 にするにはどうしたらいいの?
251デフォルトの名無しさん:2008/07/24(木) 20:00:54
>>250
regex を二回呼べばいいんでは?
252デフォルトの名無しさん:2008/07/24(木) 20:09:39

すいません 2 回呼ぶと言うのはどういう意味でしょうか?
253デフォルトの名無しさん:2008/07/24(木) 20:23:33
>>250
簡単な例をplz
254デフォルトの名無しさん:2008/07/24(木) 20:29:02
${1}0でいけたような気がしたけど、どうだったかなあ
255デフォルトの名無しさん:2008/07/24(木) 20:31:59
1.35のregexでいまためしてみた。
"\\10"で大丈夫。sed format string syntaxってやつだ。
"${1}0"はだめ。

#include <iostream>
#include <string>
#include <boost/regex.hpp>
int main()
{
    boost::regex re("(.)(.)(.)(.)(.)(.)(.)(.)(.)(.).*");
    std::string s ="abcdefghijklmn";
    std::cout << boost::regex_replace(s, re, "\\10") << std::endl;
    return 0;
}
256デフォルトの名無しさん:2008/07/24(木) 20:34:49
そういう意味か!
257250:2008/07/24(木) 20:38:51
>>255
ありがとう!それでうまくいきました.
258デフォルトの名無しさん:2008/07/25(金) 10:23:37
boost_serializationを画面やメモリに出力したいのですが教えて下さい
test_classは別に定義してあるとします。これだとファイル出力です

#include <fstream>
#include <string>

int main()
{
std::ofstream fp("XXX.xml");
boost::archive::xml_oarchive oarchive(fp);

test_class Z;
Z.a = 22; Z.b = 7;

oarchive << boost::serialization::make_nvp("Root", Z);

}

259デフォルトの名無しさん:2008/07/25(金) 10:34:45
>>258
よくわからんが
ofstreamのかわりにcoutやsstreamを使えばいいだけなんじゃないの?
260デフォルトの名無しさん:2008/07/25(金) 10:35:02
追記

型 const boost::serialization::nvp<T>の出力方法がわかればいいのですが
261デフォルトの名無しさん:2008/07/25(金) 10:36:58
トンクス これでいけました!

xml_oarchive oarchive(fp); → xml_oarchive oarchive(cout);
262デフォルトの名無しさん:2008/07/25(金) 10:41:06
メモリに格納したいのでstringにしたらエラーでました。 メモリに入れる良い方法ありませんか?

string s;
boost::archive::xml_oarchive oarchive(s);

1番目の引数を 'std::string' から 'std::ostream &' に変換できません。
263デフォルトの名無しさん:2008/07/25(金) 10:46:46
>>262
つ[stringstream]
264デフォルトの名無しさん:2008/07/25(金) 10:50:32
トンクス
265デフォルトの名無しさん:2008/07/25(金) 13:06:02
参照を使うべきかポインタを使うべきか悩んでいるのですが、
参照なんて使わない!もしくはできる限り全て参照を使う!って方いますか?
どうもポインタと参照の違いが分かりません(使いどころとして)
266デフォルトの名無しさん:2008/07/25(金) 13:46:14
>>265
C++では、ポインタを使わないといけないケース以外はポインタを使わない。
使うとしても、大抵はイテレータと言う形で使っている。
必要に迫られれば、ポインタを使うこと自体は吝かではない。
267デフォルトの名無しさん:2008/07/25(金) 13:50:08
C++だと関数にヌル終端文字列を渡すときも、const char * とか使わず、
全て const char & とか const std::string & を使うの?
268デフォルトの名無しさん:2008/07/25(金) 13:51:13
const char & を渡してどーすんだ
269デフォルトの名無しさん:2008/07/25(金) 13:58:18
俺は、参照を使わざるを得ないときと、値渡しの代わりとしてコピーのコストを抑えるためにしか、参照を使ってないな
それ以外はポインタ
270デフォルトの名無しさん:2008/07/25(金) 14:08:14
void test(const char& s){
  if(&s==NULL){
    std::cout << "(NULL)" << std::endl;
  }
  else{
    std::cout << &s << std::endl;
  }
}
int main(){
  test(*"aaa");
  test(*static_cast<const char*>(NULL));
  return 0;
}
--結果---
aaa
(NULL)


扱えないことはない。
でもまぁ正直言って、これはないw
271265:2008/07/25(金) 14:12:35
値渡しのコピーを省くためなら、参照でなくともポインタでできそうですけど、
それをわざと参照でやる理由はなんでしょう?
c++まだ勉強中で、ざっと見た感じ、以下のようなものしか有用性はないような気がしてます。
ポインタでの煩わしい明示を省ける、視覚的に区別する以外のメリットはあるのでしょうか?

int n;
int &func();

void main()
{
    int i = 0;
    func() = i;
}

int &func()
{
    return n;
}
272デフォルトの名無しさん:2008/07/25(金) 14:29:06
ポインタは参照と違ってNULLを渡すことができるらしいよ。
参照はポインタと違っていい一般保護例外を起こすようなアドレスを排除できるらしいよ。
273デフォルトの名無しさん:2008/07/25(金) 14:35:22
>>271
少なくともread-onlyな引数を、効率のためにconst参照渡しがしたいケースなら、
素直にreference使ったほうが便利だよ

>>272の言うような問題もないし、呼ぶ側としても
ただの値渡しと同じように記述できて、型変換や何かが必要な場合もコンパイラが面倒
見てくれるからな

ユーザ定義演算子などでは、意図した記法を実現したければ、
事実上参照以外に選択肢が無いこともある
274デフォルトの名無しさん:2008/07/25(金) 14:36:21
>>272
やってやれんことはないな
void hoge(double &d) { }
hoge(*(double *)NULL);
hoge(*(double *)123);
275デフォルトの名無しさん:2008/07/25(金) 14:37:23
>>271
const参照になるけど、
・良いかどうかは別にして、コンストラクタの暗黙呼び出しが使える。
・一時オブジェクトが渡せる。
という利点はある。

struct IntX {
  int n;
  IntX():n(0){}
  IntX(int argn):n(argn){}
};
void test(const IntX& a){
  std::cout << a.n << std::endl;
}
void test2(const IntX* a){
  std::cout << a->n << std::endl;
}
int main(){
  test(IntX());
  test(10);
  //test2(&IntX(20)); //左辺値でないのでコンパイル不可
  return 0;
}

あと、>>272がツッコミ入れてくれた通り、
>>270で書いた *static_cast<const char*>(NULL) みたいなネタは
実際のプログラムでやったら(無効な参照を作ったら)駄目だからね。
276265:2008/07/25(金) 14:47:48
ふむふむ、なるほど。よく分かりません\(^o^)/
もう少し理解を深めてから出直したいと思います。
277デフォルトの名無しさん:2008/07/25(金) 14:48:21
このスレか別のスレかわからないが最近同じネタをやってて、
参照が追加になったのは演算子のオーバーロードやコピーコンストラクタで
必要に迫られたからということらしい。
通常では戻り値はいいとして引数で使うと変数の変化が追いにくくなるので
多用はしないということだった。
278265:2008/07/25(金) 14:55:17
C++の機能拡張に合わせて追加された、ということでしょうか。
同じネタが上がるということは、同じ疑問を持つ人がいるということですかね。
オーバーロードやコピーコンストラクタのあたりも見直してみます。
279デフォルトの名無しさん:2008/07/25(金) 14:56:12
>>274
その場合は呼び出し元に問題があることが確定するのが、参照にしとく利点になるかな?
ポインタだと、渡された側でヌルチェックすべきかどうか気になってしまう。
280デフォルトの名無しさん:2008/07/25(金) 14:57:23
>>276
まだ勉強中って書いてあったね、ごめん。
慣れるまで、参照でなければならない箇所以外は
ポインタで良いと思うよ。

たぶん、経験が自然に教えてくれる。
281デフォルトの名無しさん:2008/07/25(金) 14:57:42
hoge(*(double *)NULL);

こんなん落ちないの?
282デフォルトの名無しさん:2008/07/25(金) 15:01:25
落ちると思って良い。
ちなみに言語規約違反な。
283デフォルトの名無しさん:2008/07/25(金) 15:04:08
間違った。規約じゃなくて規格。
284デフォルトの名無しさん:2008/07/25(金) 15:08:09
C++でC言語のキャスト使うのやめれ
285デフォルトの名無しさん:2008/07/25(金) 15:08:49
そういうときは未定義動作っていうんだ。コンパイルはできちゃうからね。
286デフォルトの名無しさん:2008/07/25(金) 15:13:29
#define NULL reinterpret_cast<void*>(0)
287デフォルトの名無しさん:2008/07/25(金) 17:21:06
BCCでの質問です。
ファイル間のインクルードの関係が以下の時、変更してないファイルも毎回コンパイルされるんですが回避策ってありますか?

A.h
B.h(include A.h)
A.cpp(include A.h)
B.cpp(include A.h,B.h)

オナがいします。
288デフォルトの名無しさん:2008/07/25(金) 17:22:52
>>287
ヘッダを変更しなければいいだけじゃないの?
289デフォルトの名無しさん:2008/07/25(金) 17:31:40
C言語勉強中なのですが、理由が知りたいです。
簡単なプログラムなのですが、回答よろしくお願いします

void hogefunc(char *);

void main()
{
char a[256] = "abc 0001";

hogefunc(a);
}

void hogefunc(char *tmp)
{
char b[256];

strcpy(b,tmp);

}
//////////////
デバッグを行うと、bの中身が"abc"のみでaの中身"abc 0001"が文字列コピーできていません。
予想だと、aの中身とbの中身は同じになると思ってました。なぜ0001が切られたのでしょうか?
よろしくお願いします
290289:2008/07/25(金) 17:34:42
全て打つ前に転送してしまいました・・
このプログラムの場合、aの中身とbの中身を同じにするにはどうすればいいでしょうか?
291デフォルトの名無しさん:2008/07/25(金) 17:34:57
そんなはずがない。なんかの見間違いなんじゃないか
292デフォルトの名無しさん:2008/07/25(金) 17:35:57
void hogefunc(char *);

void main()
{
char a[256] = "abc 0001";

hogefunc(a);
}

void hogefunc(char *tmp)
{
char b[256];

strcpy(b,tmp);

printf("%s",b);

}

で試したけどちゃんと表示されてました
293デフォルトの名無しさん:2008/07/25(金) 17:35:58
>>289>>290
んなこたぁーない
もう少しデバッグのステップ続けてみ
294デフォルトの名無しさん:2008/07/25(金) 17:36:21
>>287
どうやってコンパイルしてる?
make 使ってるのなら makefile 見せてみ
295デフォルトの名無しさん:2008/07/25(金) 17:37:42

"abc 0001"
   ^ 実はこれが\0というオチを予想
296デフォルトの名無しさん:2008/07/25(金) 19:01:40
>>288,294
どうやらファイル名が長すぎるのが原因のようでした。
最小限の再現作ってたらincludeのみのヘッダファイルが二個だけになったので^^;
297デフォルトの名無しさん:2008/07/25(金) 19:11:07
一様乱数を生成する関数のソースについて質問があります。y=1/sqrt(2)*exp(-1/2*x*x)の計算で
In function `GaussRandom':: undefined reference to 'sqrt’と In function `GaussRandom':
: undefined reference to `exp'というエラーがでて実行できません。もちろん<math.h>は定義しました。
レポート課題なのでマジで困ってます。是非教えてください。ソースを下に載せておきます。
ちなみにxが一様乱数で、yが正規乱数です。

double GaussRandom()
{
double x;
double y;

x=UniformRandom();
y=1/sqrt(2)*exp(-1/2*x*x);
return y;
}

double UniformRandom()
{
double x;
int r=1;

r=1229*r+351750;
x=r/1664501;

return x;
}
298デフォルトの名無しさん:2008/07/25(金) 19:29:31
>>297
お前いい加減にしろよ。
299デフォルトの名無しさん:2008/07/25(金) 19:53:42
>>289
変数寿命が切れてるから上書きされているんじゃないの?
300デフォルトの名無しさん:2008/07/25(金) 20:23:03
クラス内の関数ポインタでつまづいた。
分からない、全然分からない。
どこが分からないのかすら分からない。
301デフォルトの名無しさん:2008/07/25(金) 20:28:50
普通の関数ポインタはわかるのか?
じゃあメンバ関数ポインタでぐぐるんだ
302デフォルトの名無しさん:2008/07/25(金) 20:35:00
ええ、それで調べているんですけど、どうしてこんなに難解なのかと小一時間(ry
関数ポインタをメンバに含めると初期化できませんよね?こんな風に
void (*pf[])() = {hoge, piyo, foo};

もう普通に関数にした方がいいのかな……。
303デフォルトの名無しさん:2008/07/25(金) 20:39:47
オーバーロード演算子関数のポインタって取れないんですか?

X (*f)(X &, X &) = +;
X (*f)(X &, X &) = &+;
X (*f)(X &, X &) = ::+;
X (*f)(X &, X &) = &::+;
X (*f)(X &, X &) = *::+;
X (*f)(X &, X &) = operator +;
X (*f)(X &, X &) = &operator +;
X (*f)(X &, X &) = &::operator +;

とか色々試したんですが「;が足りません」だの「operatorの位置が不正です」だのなんだの
構文に文句付けられて通りません
取り方があれば教えて下さい
304デフォルトの名無しさん:2008/07/25(金) 20:42:20
それってただの関数ポインタじゃないか?
305デフォルトの名無しさん:2008/07/25(金) 20:46:28
>>303
これでいけたぞ
#include <stdio.h>
struct X{}x;
X operator+(X&, X&){printf("x");return X();}
int main(){
X (*f)(X&, X&) = operator+;
f(x,x);
}
306デフォルトの名無しさん:2008/07/25(金) 20:53:37
>>302
#include <stdio.h>
class A{
static void (A::*pf[])();
public:
void hoge(){ printf("hoge"); }
void piyo(){ printf("piyo"); }
void foo(){ printf("foo"); }
void call(){ for(int i = 0; i < 3; i++) (this->*pf[i])(); }
};
void (A::*A::pf[])() = { &A::hoge, &A::piyo, &A::foo };
int main() {
A().call();
}
307デフォルトの名無しさん:2008/07/25(金) 20:56:10
俺には解読不能な文字列が多すぎて、目眩がしそう。
308デフォルトの名無しさん:2008/07/25(金) 21:24:13
質問があるんですが,C++プログラムの変数の中に入っているデータをJAVAで取得することは可能なんでしょうか?

データベースやファイルに書き込むなどの方法を取らずに、出来る方法があれば是非知りたいです。
309デフォルトの名無しさん:2008/07/25(金) 21:27:34
>>308
JNIと相談してみてください。
310デフォルトの名無しさん:2008/07/25(金) 21:29:00
Javaって他のJavaプログラムの変数の中のデータを取得することできるの?
311デフォルトの名無しさん:2008/07/25(金) 21:30:24
>>306
ありがとうございます。
あとはゆっくり中身を理解したいと思います。
312デフォルトの名無しさん:2008/07/25(金) 22:25:34
>>310
普通にclassファイルがあれば、望みは全て叶うでしょう。
実行中のプログラムとかCORBAとかその他みたいなプロセス間通信の事を言っているのなら、そういうインターフェースを自分で作ってください。
313デフォルトの名無しさん:2008/07/25(金) 22:52:23
>>297
#include <math.h> と書いてありますか?
手元のコンパイラで試しますので、全文をどこかにアップロードしていただけますか?
314デフォルトの名無しさん:2008/07/25(金) 23:04:42
315デフォルトの名無しさん:2008/07/25(金) 23:18:23
>>312
>>308に言ってあげてください
316デフォルトの名無しさん:2008/07/26(土) 09:16:53
ビット演算で文字列中の大文字を小文字にしようとしてるのですが一文字目は出来ますがふた文字目以降ができません。
この場合ってループで回して一文字ずつ処理するしかないんですかね?
317デフォルトの名無しさん:2008/07/26(土) 09:19:56
>ビット演算で文字列中の大文字を小文字にしようとしてる
言ってる意味が分からないのでソースで。
318デフォルトの名無しさん:2008/07/26(土) 09:23:35
str |= 0x20;
としか・・・
319デフォルトの名無しさん:2008/07/26(土) 09:44:13
OK、では次はこれをソースで。
>のですが一文字目は出来ますがふた文字目以降ができません。
320デフォルトの名無しさん:2008/07/26(土) 09:45:24
OKってようするに、わからないなら答えなくっていいです。
ソースだせソースだせってわからないだけでしょ?それをソースだせって馬鹿なの?
321デフォルトの名無しさん:2008/07/26(土) 09:48:35
ソースが無くてトンカツが食えるか!
322デフォルトの名無しさん:2008/07/26(土) 09:48:51
323デフォルトの名無しさん:2008/07/26(土) 09:52:29
1レス目でソース出してれば1レスで問題点が返ってくるレベルと予想
324デフォルトの名無しさん:2008/07/26(土) 09:56:49
文字列がマルチバイトを含まないことを祈るばかりです。
325デフォルトの名無しさん:2008/07/26(土) 12:29:55
一文字目は出来てる>>316さんがマルチバイト文字くらいで困るわけ無いじゃないか
326デフォルトの名無しさん:2008/07/26(土) 12:59:33
>>309
JNIを調べて試してみましたが,自分の場合は使えなさそうです.
JAVAソースを書いて→ヘッダー作成→C++ソース作成
という順序のようですが,今の状態ではC++ソースとJAVAソースが全然別のアプリケーションとして完成していて,
C++アプリで使っているデータをJAVAで扱いたいという事なんですが…。
C++でデータを自分自身のIPに送って,JAVAでそれを取得するというのを今考えているんですが….
327デフォルトの名無しさん:2008/07/26(土) 13:04:53
テキストファイルに書き込む→読み込む
328デフォルトの名無しさん:2008/07/26(土) 13:06:25
自前でシリアル化して通信すれば
329デフォルトの名無しさん:2008/07/26(土) 13:19:36
>>10
(2)だと、クッキーの設定はちゃんとしてるのに書き込み確認画面のまま止まってる。
つまりクッキーの設定がうまくいってないみたいなんだが、デバッガで文字列を確認してみても正常だし
そのデバッガで確認した文字列を手動で書いて送信するとうまくいく。
330デフォルトの名無しさん:2008/07/26(土) 13:20:27
すみません誤爆しました。
331デフォルトの名無しさん:2008/07/26(土) 14:00:26
>>327
それでも一応可能なんですが,
取得したデータに対応した動きみたいなモノを作らないといけない為,
JAVA側でテキストファイルをずっと参照し続け,更新があった場合○○する.
といった風な感じになってずっと参照し続けるというのが気持ち悪いから避けたいんです.
332デフォルトの名無しさん:2008/07/26(土) 14:01:00
>>326
プロセス間通信とか、XMLでシリアライズしたのを渡すとか。
333デフォルトの名無しさん:2008/07/26(土) 14:55:33
1〜10までの偶数を書き出すプログラムでもっと簡単なコードがあったら教えてください。
自分で書いたのは↓です。
#include <iostream>
using namespace std;

int main()
{
int i;

cout << "1〜10までの偶数を出力します\n";

for(i = 1; i <= 10; i++){
if(i % 2 == 1){
continue;
}
cout << i << "です\n";
}
return 0;
}
334デフォルトの名無しさん:2008/07/26(土) 14:56:34
for(i = 2; i <= 10; i+=2){
cout << i << "です\n";
}
335デフォルトの名無しさん:2008/07/26(土) 14:58:06
for(i = 1; i <= 5; i++) cout << 2*i << "です\n";
336デフォルトの名無しさん:2008/07/26(土) 14:59:02
>>334 335

ありがとうございます
337デフォルトの名無しさん:2008/07/26(土) 14:59:38
cout << "2, 4, 6, 8, 10です\n";
338デフォルトの名無しさん:2008/07/26(土) 15:01:39
ウケタw
339デフォルトの名無しさん:2008/07/26(土) 15:07:52
そんなに面白くはない
340デフォルトの名無しさん:2008/07/26(土) 15:08:35
↓次の方どうぞ
341デフォルトの名無しさん:2008/07/26(土) 15:31:54
繰り返し文を利用して

☆☆
☆☆☆
☆☆☆☆
☆☆☆☆☆
と表示させるコードを書いてみたのですが、もっと簡単に書く方法ありませんか?

#include <iostream>
using namespace std;

int main()
{
int i;

for(i = 1; i <= 5; i++){
if(i == 1){
cout << "☆\n";
} else if (i == 2){
cout << "☆☆\n";
} else if (i == 3){
cout << "☆☆☆\n";
} else if (i == 4){
cout << "☆☆☆☆\n";
} else if (i == 5){
cout << "☆☆☆☆☆\n"; }
}
return 0;
}
342デフォルトの名無しさん:2008/07/26(土) 15:34:26
ひょっとしてそれはギャグで言っているのか?
343デフォルトの名無しさん:2008/07/26(土) 15:35:55
普通の小学生ならカウンタの値と☆の数に関連性を見出せる筈
344デフォルトの名無しさん:2008/07/26(土) 15:36:47
>>341
cout << "☆\n☆☆\n☆☆☆\n☆☆☆☆\n☆☆☆☆☆";
345デフォルトの名無しさん:2008/07/26(土) 15:41:25
>>341
そこはif文じゃなくて、switchで場合分けするべきだと思うんだ。
346デフォルトの名無しさん:2008/07/26(土) 15:42:47
>>345
いやswitchにしてもまだおかしいだろwwww
347デフォルトの名無しさん:2008/07/26(土) 15:44:04
少し考えるので時間ください
348デフォルトの名無しさん:2008/07/26(土) 15:46:10
hoshiHyouji(size_t nannko)という関数を作ればいいんじゃに
349デフォルトの名無しさん:2008/07/26(土) 15:53:45
関数はまだ習ってないのでわからないです。

#include <iostream>
using namespace std;

int main()
{
int i;
int j;

for(i = 1; i <= 5; i++){
for(j = 1; j <= i; j++){
cout << "☆";
}
cout << '\n';
}
return 0;
}

これでも同じように表示されたましたけど 考え方はあってますか? それとも、もっと簡単な方法があるのでしょうか?
350デフォルトの名無しさん:2008/07/26(土) 15:56:42
あってると思うけど
個人的に
for(i = 0; i < 5; i++){
for(j = 0; j < i; j++){
の方が好き
351デフォルトの名無しさん:2008/07/26(土) 15:58:14
>>350
なるほど0からのカウントですか。

もっと分かりやすいコードが書けるように頑張ってみます。
352デフォルトの名無しさん:2008/07/26(土) 15:58:55
>>349
そこは繰り返しじゃなくて再帰を使うべきだな。

void print_hosi(int num);
void print_hosi(int num)
{
    if ( num <= 0 ) { return; }
    for ( int i = 0; i < num; i++ ) { cout << "☆"; }
    cout << endl;
    print_hosi( num - 1 );
}
353デフォルトの名無しさん:2008/07/26(土) 16:10:37
>>350 すいません、自分が指摘するのはあれなんですが

☆☆
☆☆☆
☆☆☆☆
☆☆☆☆☆
と表示させるなら

for(i = 0; i < 5; i++){
for(j = 0; j <= i; j++){
だと思います。
354デフォルトの名無しさん:2008/07/26(土) 16:14:39
俺なら
for(i = 0; i < 5; i++){
for(j = 0; j < i+1; j++){
にするかな、気分の問題だけど
355デフォルトの名無しさん:2008/07/26(土) 16:17:28
for(i = 1; i <= 5; i++)
for(j = 0; j < j; j++)
356デフォルトの名無しさん:2008/07/26(土) 16:18:08
俺には j < i であってるように見える。
357デフォルトの名無しさん:2008/07/26(土) 16:19:28
>>356
それで実行したら
-----------
改行

☆☆
☆☆☆
☆☆☆☆
-----------
でした。
358デフォルトの名無しさん:2008/07/26(土) 16:19:33
359デフォルトの名無しさん:2008/07/26(土) 16:29:21
まぁ
for(i = 0; i < 5; i++){ cout << "☆";
for(j = 0; j < i; j++){ cout << "☆";
}
cout << "\n";
}
でも出来るけど、>>355が正解だろうな。
360デフォルトの名無しさん:2008/07/26(土) 16:45:24
でもこの手のはCSVやURLクエリのように区切りが出てきて
for(int i=0; i<5; i++){
 std::cout << "☆";
 for(int j=0; j<i; j++){
  std::cout << ",";
  std::cout << "☆";
 }
 std::cout << "\n";
}
みたいな感じに落ち着くことも多い。
361デフォルトの名無しさん:2008/07/26(土) 16:47:44
#include <iostream>
#include <iomanip>

int main() {
int i, j;
std::cout.fill('☆');
for(i = 1; i <= 5; i++)
std::cout<<std::setiosflags(std::ios::right)<<std::setw(i)<<""<<std::endl;
return 0;
}
362デフォルトの名無しさん:2008/07/26(土) 17:00:18
('☆')←何この顔バカにしてるの?
363デフォルトの名無しさん:2008/07/26(土) 17:09:26
>>362
なんだと
364デフォルトの名無しさん:2008/07/26(土) 17:09:38
std::string str;
for(int i=0; i < 5; i++) {
 str += "☆";
 std::cout << str;
}
std::cout << "\n";
365デフォルトの名無しさん:2008/07/26(土) 17:11:16
>>362
寄生獣ですね、わかります。
366デフォルトの名無しさん:2008/07/26(土) 19:54:58
サービスとして動くプログラムのサンプルをやってるんですが上手くいきません
StartServiceCtrlDispatcher()で失敗します
GetLastError()で1063が取れるんですけど、どうすればいいんでしょうか?
環境はxp sp2、vc++2005でやってます

void ErrorHandler( char *s, DWORD err )
{
std::cout << s << std::endl;
std::cout << "Error number: " << err << std::endl;
ExitProcess( err );
}

void WINAPI ServiceMain( DWORD argc, LPTSTR *argv )
{
// 空
}

void main()
{
char *SERVICE_NAME = "BeepService";

SERVICE_TABLE_ENTRY serviceTable[] = {
{ SERVICE_NAME, (LPSERVICE_MAIN_FUNCTION)ServiceMain },
{ NULL, NULL }
};

// SCMで登録する
BOOL success = StartServiceCtrlDispatcher( serviceTable );
if( !success )
ErrorHandler( "In StartServiceCtrlDispatcher", GetLastError() );
}
367デフォルトの名無しさん:2008/07/26(土) 20:23:00
>>366
よくわからんが、ちゃんとサービスとしてSCMのデータベースに登録済みで、
SCMからサービスとして起動されたときにそういうエラーが出ているの?

ただのコンソールアプリとして普通にキックしたときに
StartServiceCtrlDispatcher()が失敗するのはただの仕様なんじゃないの
368デフォルトの名無しさん:2008/07/26(土) 22:02:45
double型の変数を文字型の変数に疑似変換するプログラムを書けと教授に言われたのですが、
全く方法が解りません・・・。
誰か助けてください。
その際関数のオーバーロードを必ず使用する事、と言われました。

実は問題の意味があまり分かってなかったり。疑似変換とは・・・?
369デフォルトの名無しさん:2008/07/26(土) 22:05:40
問題の意味は出題者に訊くしかない
370デフォルトの名無しさん:2008/07/26(土) 22:08:25
今から教授に電話して聞いてみます。
371デフォルトの名無しさん:2008/07/26(土) 22:10:58
sprintf?
でもオーバーロードなんか必要ないしなぁ・・・
372デフォルトの名無しさん:2008/07/26(土) 22:13:17
留守電だったので諦めました。
とりあえず考えられる事をいくつかプログラムしてみます。
疑似変換・・・・か。
373デフォルトの名無しさん:2008/07/26(土) 22:20:58
char型の固定小数で表せって事だろJK
374デフォルトの名無しさん:2008/07/26(土) 22:22:31
>>368
こんなん?
真夜中の電話、不吉な感じがイヤン

#include<iostream>
#include<string>

//ここでオペレータをほげほげ

int main(void){
double x=1.2345;
std::string str;

str=x;
std::cout << str << std::endl;

return 0;
}
375デフォルトの名無しさん:2008/07/26(土) 22:33:26
オーバーロードを入れるとややこしくなりそうだな〜
376デフォルトの名無しさん:2008/07/26(土) 22:37:31
関数のオーバーロードをする必要性がわからん・・
377デフォルトの名無しさん:2008/07/26(土) 23:15:40
inline関数を使う場合は関数の宣言と関数の定義で2回記述しないといけないんですか?
#include <iostream>
using namespace std;
//関数の宣言
inline int square(int x);
inline double square(double x);
int main()
{
int i;
double j;

cout << "整数を入力してください\n";
cin >> i;
int sum1 = square(i);
cout << i << "の二乗は" << sum1 << "です\n";

cout << "小数を入力してください\n";
cin >> j;
double sum2 = square(j);
cout << j << "の二乗は" << sum2 << "です\n";

return 0;
}
//関数の定義
inline int square(int x){
int num1;
num1 = x * x;
return num1;
}inline double square(double x){
double mum1;
mum1 = x * x;
return mum1;}
378デフォルトの名無しさん:2008/07/26(土) 23:19:47
>>377
inline なら定義が無いと意味無いし、定義は宣言を含むから、定義だけ書いとけばいいよ。
379デフォルトの名無しさん:2008/07/26(土) 23:21:06
>>378 即レスありがとうございます!
380デフォルトの名無しさん:2008/07/26(土) 23:28:40
すいませんもう1つだけ質問です。
テンプレート関数は

templat <class T>
381デフォルトの名無しさん:2008/07/26(土) 23:29:25
すいません誤爆で途中で投稿してしまいました。
スレ汚しすいません;;
382デフォルトの名無しさん:2008/07/26(土) 23:34:20
すいませんテンプレート関数は
template <class T>
T square(T x){
処理
}
と記述できると書いてあったんですが
宣言と定義みたいに分けて記述することはできないんですか?
試しに
//宣言
template <class T>
T square(T x);

main関数

return 0;
//定義
T square(T x){
処理
}
とやったのですがエラーが出ました。要するに無理ってことでしょうか?
383デフォルトの名無しさん:2008/07/26(土) 23:43:04
>>382
無理です。使う時点で定義が読み込まれている必要があります。
384デフォルトの名無しさん:2008/07/26(土) 23:44:15
>>383
ありがとうございます。
不思議に思っていたことが解決しました。
385デフォルトの名無しさん:2008/07/26(土) 23:44:31
>>382-383
っ export
386デフォルトの名無しさん:2008/07/26(土) 23:52:22
>>385
つ現実
387デフォルトの名無しさん:2008/07/27(日) 00:02:31
388デフォルトの名無しさん:2008/07/27(日) 00:06:47
>>387
馬鹿?
389デフォルトの名無しさん:2008/07/27(日) 00:08:34
>>382
分けて書くこと自体は可能。その感じだと、たぶん定義のほうに template <class T> が足りないだけ。
390デフォルトの名無しさん:2008/07/27(日) 01:35:03
「aaaaiiiuuueooあああああいいいしてるるるる」
みたいに、

・昇順で並んでいる
・同じ文字がたくさん入ってる
・あとから変更されることはない
・wchar_t
・一文字あたりの繰り返しは少ない(5個くらいまで)
・長い文字列もある(10MBytesくらい)

という文字列を扱うんだが、

・「N番目の文字」を高速に取り出せる
・「N種類目の文字と個数」を高速に取り出せる

条件を満たすデータ構造ってどんなのがある?
配列を2つ用意するしかない?

てかこのスレでよかった?
391390:2008/07/27(日) 01:36:00
すまん矛盾してた

> ・同じ文字がたくさん入ってる
これは無視してくれ。
392デフォルトの名無しさん:2008/07/27(日) 01:41:12
>>390
struct { int start; wchar_t c; } を start でソートした配列、でいいんじゃないかな?
その例だと {{0, L'a'}, {4, L'i'}, {7, L'u'}, {10, L'e'}, {11, L'o'}, {13, L'あ'}, ...} って感じで。
393デフォルトの名無しさん:2008/07/27(日) 01:41:14
>>390
昇順に並んでるってのは、文字コードが昇順にならんでるってわけじゃないの?
394デフォルトの名無しさん:2008/07/27(日) 01:46:54
>>392
おお!
なんだかよさそうだ。
ありがと!

>>393
そうです
395デフォルトの名無しさん:2008/07/27(日) 01:48:28
>>394
例にでてる文字列が文字コード順に並んでないけど、それは例が間違いってことだな。
396デフォルトの名無しさん:2008/07/27(日) 01:50:47
>>395
ひらがなが先だっけ?
なら例が間違ってるわ。
すまん
397デフォルトの名無しさん:2008/07/27(日) 01:53:16
>>396
いや、アルファベットをローマ字で昇順に並べても、文字コード順にはならんよ。
398デフォルトの名無しさん:2008/07/27(日) 10:26:24
>>397
そうでした
399デフォルトの名無しさん:2008/07/27(日) 14:51:23
#include <iostream>
using namespace std;

//関数addの宣言

void add(int *px, int *py, int *pz);

//点数を加算するプログラム

int main()
{
int x1;
int x2;
int a;

cout << "2科目の点数を入力してください\n";

cin >> x1 >> x2;

cout << "加算する点数を入力してください\n";

cin >> a;

add(&x1, &x2, &a);

cout << "科目1は" << x1 << "点です\n";
cout << "科目2は" << x2 << "点です\n";
return 0;}
//関数addの定義
void add(int *px, int *py, int *pz){
*px += *pz;
*py += *pz;}
400デフォルトの名無しさん:2008/07/27(日) 14:53:22
2科目のテストの点数(x1,x2)にa点を加算する関数add()を、ポインタを使って定義しなさい。
という宿題が出たのですが、これで実行したら成功したのですが。
これは無駄過ぎるという所はありませんか?
あったら指摘お願いします
401デフォルトの名無しさん:2008/07/27(日) 14:55:17
宿題スレに書かずにここに書く辺りが無駄。
402デフォルトの名無しさん:2008/07/27(日) 15:00:46
>>400
まあパッと見pzはポインタにする必要はまったくないな。
403デフォルトの名無しさん:2008/07/27(日) 15:01:49
宿題スレは〜のコード書いてくださいとかだと勝手に解釈してたので
こっちの方に書き込んでしまいました。
ご迷惑おかけして大変申し訳ございませんでした。
この場を借りて謝罪いたします。
404デフォルトの名無しさん:2008/07/27(日) 15:05:10
>>402
指摘ありがとうございます。
405デフォルトの名無しさん:2008/07/27(日) 17:59:33
template<class T, class U>
void f(T t, U u)
{
  ...
}

template<class T>
void f<T, int>(T t, int u)
{
  ...
}

こういうことってできないんだっけ?
error C2768: 'f' : 明示的なテンプレート引数を使用することはできません。
って出るんだが。
406デフォルトの名無しさん:2008/07/27(日) 18:01:19
<T, int>いらない
407デフォルトの名無しさん:2008/07/27(日) 18:04:36
>>406
ありがとうさん
408405:2008/07/27(日) 18:07:53
template<int I, int J>
void f()
{
}

template<int I>
void f<I, 0>()
{
}

これは無理?
J=0の場合のみ特殊化。
409デフォルトの名無しさん:2008/07/27(日) 18:11:11
テンプレート使った際の演算子オーバーロードで悩んでいます。
コンパイルエラーは以下のように出ます。
-------------------------
Test.cpp:13: error: expected constructor, destructor,
or type conversion before ‘Test’
-------------------------
このエラーを理解できないため、デバグできません。
どうしたらいいのでしょうか?
教えてください。

ソースは以下。
410デフォルトの名無しさん:2008/07/27(日) 18:12:25
// Test.cpp
#include<iostream>
using namespace std;

template<typename T>
class Test{
 public:
  T value;
  Test(){};
  Test operator+(const Test& t);
};

template<typename T>
Test Test<T>::operator+(const Test<T>& t) //←13行目
{
 Test tmp;
 tmp.value = value + t.value;
 return tmp;
}

int main()
{
 Test<int> test1, test2;
 test1.value=100;
 test2.value=200;
 Test<int> test3 = test1 + test2;
 return 0;
}
-------------------------
411デフォルトの名無しさん:2008/07/27(日) 18:15:34
Test<T> Test<T>::operator+(const Test<T>& t)
じゃない?

const Test<T> Test<T>::operator+(const Test<T>& t)
このほうがいいかな
412410:2008/07/27(日) 18:25:03
おお!
ありがとうございます m(_ _)m

続けて質問して申し訳ないのですが、
const をつけると付けないとではどのようなちがいがあるのでしょうか?
413デフォルトの名無しさん:2008/07/27(日) 18:34:16
クラスのメンバ変数をポインタ型にすると
メンバ変数が定義されていないとか言うんだけど
何これ…
414413:2008/07/27(日) 18:41:51
間違えた
メンバ変数じゃなくてメンバ関数をポインタ型にすると
メンバ変数が定義されていないって出る
415デフォルトの名無しさん:2008/07/27(日) 18:42:39
class hoge{
416デフォルトの名無しさん:2008/07/27(日) 18:46:14
直感で
static付けたらどうでしょうと言ってみよう
417デフォルトの名無しさん:2008/07/27(日) 18:48:36
メンバ関数をポインタ型?
メンバ変数をメンバ関数ポインタの型にするって事か?
418デフォルトの名無しさん:2008/07/27(日) 18:54:38
>>417
class A{
    praivate:
     int *a;
    public:
     void *get_a();
}
void A::*get_a()
{
  return a;
}

aが定義されていない識別子です

ってなる
419デフォルトの名無しさん:2008/07/27(日) 18:56:44
void* A::get_a()
420デフォルトの名無しさん:2008/07/27(日) 18:58:56
voidじゃなくてintだった…
>>419
解決した。ありがとう!
421デフォルトの名無しさん:2008/07/27(日) 18:59:27
すみません。。。お尋ねしたいのですが、
GDBでUTF-8の内容を表示させるにはどうすればよいのでしょうか?
ご存知の方がいらっしゃいましたら何卒ご教授下さい。
よろしくお願いいたします。
422デフォルトの名無しさん:2008/07/27(日) 19:37:58
TCHAR pString[64] ;
std::wcin.getline(pString, 64) ;

が入力を待たずに終わってしまいます。
プロジェクトを別に作って試したんですが他ではちゃんと入力を待ってます。

どういう状況の時だと処理を待たずに終了してしまうのでしょうか?
423デフォルトの名無しさん:2008/07/27(日) 19:52:06
>>422
現象とは関係ないけど、それ、wchar_tかWCHARを使ったほうがいいよ。
424デフォルトの名無しさん:2008/07/27(日) 20:15:58
>>422
直前で数値や文字列を入力したときに改行が残ったままになってるとか
425デフォルトの名無しさん:2008/07/27(日) 20:25:08
文字列に指定した文字がいくつあるか調べる関数を作成して、実際にキーボードから文字を入力して文字の個数を調べるコードを書いたのですが。
include <iostream>
#include <string>
using namespace std;

//関数countの宣言
int count(char str[], char ch);

//指定した文字数を調べるプログラム

int main()
{
char str[256]; //入力する文字列
char c; //調べる文字
int sum; //文字数

cout << "文字列を入力してください\n";
cin >> str;

cout << "探したい文字を入力してください\n";
cin >> c;

sum = count(str, c);

cout << str << "の中に" << c << "は" << sum << "個あります\n";
return 0;
}
426デフォルトの名無しさん:2008/07/27(日) 20:26:14
//関数countの定義
int count(char str[], char ch){
int j; //文字列の文字数
int i;
int num = 0; //カウントする変数

j = strlen(str);

for(i = 0; i < j; i++){
if(str[i] == ch){
num++;
}
}
return num;
}

これで実行してちゃんとカウントできたのですが、無駄過ぎる文はありませんか?
指摘お願いします。
連投すいません;; 
427デフォルトの名無しさん:2008/07/27(日) 20:29:50
>>426
sum = std::count( str.begin(), str.end(), c )

428デフォルトの名無しさん:2008/07/27(日) 20:30:22

 std::string と std;;wstring で template を使って関数を共通化したいんだけど,
文字列リテラル ( "hoge" と L"hoge") や,文字型の違い ( 'a' と L'a') を吸収するには
どうやったらいいの?

 例えば,バックスラッシュを付け足す場合とか.

template <typename string_type>
string_type& AddBackSlash(string_type& str)
{
  return str += '\\';//← wstring の場合は L'\\' にしたい,
}
429デフォルトの名無しさん:2008/07/27(日) 20:31:09
>>427
ありがとうございます!
430デフォルトの名無しさん:2008/07/27(日) 20:37:12
>>428
特殊化
431デフォルトの名無しさん:2008/07/27(日) 20:58:44
おすすめのエディタ教えてください!
今までC言語を始めよう!というフリーソフトを使ってきました
432428:2008/07/27(日) 21:13:16

>>430 ありがとうございます.特殊化するということはコピペして,wstring に置換して, L を付ける作業をするしかないですかね…

template <typename string_type>
string_type& AddHoge(string_type& str)
{
  string_type strInternal = "foo";
  return str += "Hoge";
}

//特殊化
template<>
std::wstring& AddHoge<std::wstring>(std::wstring& str)
{
  std::wstring strInternal = L"foo";
  return str += L"Hoge";
}
433デフォルトの名無しさん:2008/07/27(日) 21:32:49
>>423-424
ありがとうございます、>>424さんが言われたとおり直前で数値をwcinにて
受け取ってます。それをコメントアウトしたらgetineのとこで処理が
止まりました。

原因はわかったのですがどうやって回避してよいのでしょうか?^^;
434デフォルトの名無しさん:2008/07/27(日) 21:41:25
std::vector<double> v(100);
このとき確保されるメモリは実装しだい?
435デフォルトの名無しさん:2008/07/27(日) 21:56:05
はい。sizeof(double)*100かもしれませんし、*128かもしれません。
436デフォルトの名無しさん:2008/07/27(日) 21:57:02
>>431
結局は好みだから使ってみて気にいったのを使えよ。
因みに俺はemacs使ってる。
437デフォルトの名無しさん:2008/07/27(日) 22:03:18
>>426

 strlen(str) で文字列の末尾まで '\0' を検索した後に,
再び文字を検索するのが無駄と言えば無駄かも.


int count(const char str[], const char ch)
{
  int num = 0; //カウントする変数

  while( *str != '\0' ) if( *str++ == ch ) num++;

  return num;
}
438デフォルトの名無しさん:2008/07/27(日) 22:08:45
int count(const char * const str, const char ch)
{
unsigned num = 0;
for (char const * p = str; (p = strchr(p, ch)) != NULL; ++p) ++num;
return num;
}
439デフォルトの名無しさん:2008/07/27(日) 23:13:07
nul終端文字列ってほんと頭悪い仕様だよな。色々非効率だし。
440437:2008/07/28(月) 01:14:04

>>438 そんなに変わらないだろうと思ってたけど,ずいぶん速いな
441デフォルトの名無しさん:2008/07/28(月) 01:34:49
>>439
PASCAL stringを授けよう。
442デフォルトの名無しさん:2008/07/28(月) 02:20:14
メッセージプロシジャでWM_CHARが送られてきた時、
OnKeyDownという関数にwpとlpをそのまま渡しています。
そして、押されたキーが"v"だった時だけ処理をしたいのでstrcmpを使ってみたのですが
そこで強制終了してしまいます。正しくはどう書いたらよいのでしょうか?
教えてください。お願いします。

OnKeyDown(WPARAM wp, LPARAM lp)
{
switch(wp)
{
case VK_RETURN:
break;



default:
if(strcmp((char*)wp,"v") == 0)
{
//キーがvだった時の処理
}
}
443デフォルトの名無しさん:2008/07/28(月) 02:26:08
>>442
一文字だったら *(char*)wp == 'v' とかでどうなんだろう
あとメッセージボックスなんかでwpの中身確認してみたらどうだろうか

ついでにこっちの方が回答もらいやすいかもね
Win32API質問箱 Build68
http://pc11.2ch.net/test/read.cgi/tech/1215348804/
444デフォルトの名無しさん:2008/07/28(月) 02:31:31
>>443
MessageBoxに表示させようと
wpをchar*にキャストしたら同じように落ちました・・・
とりあえずそっちで聞いてきます。
ありがとうございました。
445デフォルトの名無しさん:2008/07/28(月) 11:16:35
初心者ですがC言語を覚えるには数学ができないと駄目ですか?
446デフォルトの名無しさん:2008/07/28(月) 11:19:21
C言語だけなら算数が出来れば十分
3Dやら暗号やら圧縮やらを扱いたいなら数学が必要になってくるかも
447デフォルトの名無しさん:2008/07/28(月) 11:21:27
446さんありがとうございます。
448デフォルトの名無しさん:2008/07/28(月) 11:29:53
C言語で仮に3Dアクションゲームを造るとすると最低限高校1年の数学と物理が理解できればチャレンジしても無謀ではないですか?
数学:sin cos tan(三角関数?)等
物理:ベクトル等
449デフォルトの名無しさん:2008/07/28(月) 11:34:01
うん、あと行列がわかってれば
物理演算しようってわけじゃないんだから、完全な理解も必要なし
450デフォルトの名無しさん:2008/07/28(月) 11:39:08
ライブラリ使えば自分で計算する必要ももちろんないしね
451デフォルトの名無しさん:2008/07/28(月) 13:18:58
まぁ行列分かってれば中学生でもできるよ。
452デフォルトの名無しさん:2008/07/28(月) 14:03:08
まぁそれをいったら
ベクトルが分かっててプログラミングができるなら小学生にもできるよ、って話だけどな
453デフォルトの名無しさん:2008/07/28(月) 14:04:41
ベクトルも行列もプログラミングも分からない大学生にはできないといいたい訳だな
454デフォルトの名無しさん:2008/07/28(月) 14:13:46
分からなきゃ勉強するまでさ。
今までだってそうやってきただろ?
455デフォルトの名無しさん:2008/07/28(月) 14:15:05
>>454
>>453 に例示されるような人はおそらく勉強しないでしょう
456デフォルトの名無しさん:2008/07/28(月) 14:27:06
スレ違いだと思いますが流れ的に質問させてください。
CとC++とwindowsプログラミングを一通り勉強したので
次にDirectXの勉強をしようと思っているのですが、勉強する前に三角関数・ベクトル・行列を復習してから(曖昧なので)
DirectXの勉強をしたほうが理解が深まると思うのですがどう思いますか?

先輩方アドバイスよろしくお願いします。
457デフォルトの名無しさん:2008/07/28(月) 14:29:49
先にDirectXのチュートリアルでもやった方が良い
458デフォルトの名無しさん:2008/07/28(月) 14:30:12
>>456
目的にもよりますが Direct3D を勉強しながら分からないところを調べるほうがオススメ
459デフォルトの名無しさん:2008/07/28(月) 14:30:21
DirectX進めながら解らないところが出るたびに数学の教科書を見るのでも別に構わんとは思う
460デフォルトの名無しさん:2008/07/28(月) 14:33:25
1からやるわけでもないしな。
思い出すのなら必要なことが出てからでも、今やってることが止まることも無いでしょう。
461デフォルトの名無しさん:2008/07/28(月) 14:37:48
DirectX=3Dじゃないと思うんだけど
462デフォルトの名無しさん:2008/07/28(月) 14:38:01
>>457 >>458 >>459 >>460
アドバイスありがとうございます。
この夏休みでDirectXの基本をマスターして3Dゲームが作れるようにがんばります。
463デフォルトの名無しさん:2008/07/28(月) 14:38:45
>>461
そうなんですか?
勘違いしていたみたいです・・。
もう少し調べてみます。
464デフォルトの名無しさん:2008/07/28(月) 14:43:38
>>461
DirectXの描画は基本3Dじゃなかったっけ
465デフォルトの名無しさん:2008/07/28(月) 14:47:03
Drawが葬られたからね。
466デフォルトの名無しさん:2008/07/28(月) 14:48:25
実はDirectSoundだけ使いたい・・・なんてことはないか
467デフォルトの名無しさん:2008/07/28(月) 14:49:42
>>464-465
そうだった
昔2D描画用のがあったんだけどもうなくなったんだね
あれ結構評判良かったのに
468デフォルトの名無しさん:2008/07/28(月) 16:02:03
今でもDirectDrawは使えるし、地味にアップデートもされてる(もうされないだろうけど)
ドキュメントが無くなったけどな
469デフォルトの名無しさん:2008/07/28(月) 16:38:04
引数←読み方インスウだと思ってたけど
ヒキスウって最近知った
470デフォルトの名無しさん:2008/07/28(月) 16:48:16
returnされる値は
カエリチ?ヘンチ?
471デフォルトの名無しさん:2008/07/28(月) 16:48:56
返り血
472デフォルトの名無しさん:2008/07/28(月) 16:53:39
>>469
どーぞくハケーン
473デフォルトの名無しさん:2008/07/28(月) 16:54:36
独学でやってたってことかな
授業とかでやったら確実に発音するでしょ
474デフォルトの名無しさん:2008/07/28(月) 16:58:05
>>470
俺はモドリチ
475デフォルトの名無しさん:2008/07/28(月) 17:00:15
普通、戻り値だよな
476デフォルトの名無しさん:2008/07/28(月) 17:03:54
オレも返り値は返り血に聞こえるから戻り値
477デフォルトの名無しさん:2008/07/28(月) 17:05:45
リターンチだろ
478デフォルトの名無しさん:2008/07/28(月) 17:07:41
どれも同じだ
479デフォルトの名無しさん:2008/07/28(月) 17:12:31
スタックの血を浴びて 〜社会不適応者のデスマーチ奮闘記〜
480デフォルトの名無しさん:2008/07/28(月) 17:37:50
新ジャンル:仕事人間サスペンスホラー
481デフォルトの名無しさん:2008/07/28(月) 20:39:33
ああ、よく考えたら俺も戻り血だったわ。
482デフォルトの名無しさん:2008/07/28(月) 20:52:11
オレは「戻り値として0を返す」とかいう。
でも「返り値として0を戻す」はいったことないな。
483デフォルトの名無しさん:2008/07/28(月) 21:21:23
俺は「返り値として」には違和感がある
返り値を使うなら「返り値をaに戻す/返す/当てる」とかは言う
返り値の値に言及する時は思いつかない
484デフォルトの名無しさん:2008/07/29(火) 00:56:44
const std::string& GeRefOfFuncStaticString(int n)
{
  static std::string str = boost::lexical_cast<std::string>(n);
  return str;
}

const std::string g_strNotFound("NotFound");

const std::string& GeRefOfFuncStaticString2(int n)
{
  static std::map<int,std::string> mapStr;
  if( mapStr.empty() )
  {
    mapStr.insert( std::make_pair(100, "100") );
    mapStr.insert( std::make_pair(101, "101") );
  }

  std::map<int,std::string>::const_iterator itrFound = mapStr.find(n);
  return itrFound != mapStr.end() ? itrFound->second : g_strNotFound;
}

int _tmain(int argc, _TCHAR* argv[])
{
  std::cout << GeRefOfFuncStaticString( 100 ) << std::endl; // 表示: 100
  std::cout << GeRefOfFuncStaticString( 101 ) << std::endl; // 表示: 100 ← 関数内の static 変数の参照を取り出せない
  std::cout << GeRefOfFuncStaticString2( 100 ) << std::endl; // 表示: 100
  std::cout << GeRefOfFuncStaticString2( 101 ) << std::endl; // 表示: 101
  return 0;
}

 map を使った場合の GeRefOfFuncStaticString2( ) は意図した動作になるんですが,たまたまでしょうか?
485デフォルトの名無しさん:2008/07/29(火) 01:24:05
>std::cout << GeRefOfFuncStaticString( 101 ) << std::endl; // 表示: 100 ← 関数内の static 変数の参照を取り出せない

関数内のstatic変数の参照を取り出してますよ。
486デフォルトの名無しさん:2008/07/29(火) 01:43:11
>>485 解答ありがとうございます.恥ずかしながら static に関してすごい勘違いをしていたようです.
 初期化が一度しか行われないんですね.以下のようにして GeRefOfFuncStaticString() でも望みどおりの
動作が出来るようになりました.
 有難うございました.

const std::string& GeRefOfFuncStaticString(int n)
{
  static std::string str;
  str = boost::lexical_cast<std::string>(n);
  return str;
}
487デフォルトの名無しさん:2008/07/29(火) 03:24:06
a
488デフォルトの名無しさん:2008/07/29(火) 07:50:00
static変数が緊急対応以外で必要になったときは設計ミス。
489デフォルトの名無しさん:2008/07/29(火) 08:06:38
何故static変数にいちいち保存しているのかが謎。
490デフォルトの名無しさん:2008/07/29(火) 09:24:49
便乗質問なんだけど

const std::string& GeRefOfFuncStaticString(int n)
{
  static std::string str = boost::lexical_cast<std::string>(n);
  return str;
}

これ static のところ、いつ初期化されるんだ? 今までプログラム
起動時(main以前)だと思ってたんだが、nが関数の呼び出し時に
決まるじゃん。

内部で
if(関数の初回呼び出しなら){
  str = boost::lexical_cast<std::string>(n);
}

みたいなコードにコンパイルされるわけ?
>>484の挙動見ているとそう見えるんだが…
491デフォルトの名無しさん:2008/07/29(火) 09:36:58
>>490
それであってる。
ちなみに初期化についてスレッドセーフである保証は無いので、
マルチスレッドのプログラムで排他せずにstatic変数使ったら、
いつ異常動作してもおかしくない。
492デフォルトの名無しさん:2008/07/29(火) 10:07:55
標準ライブラリのメンバ関数までが詳細に載ってるページってありますか?
探したけど俺の目が悪いんだろうか、見つかりません;;
だれか教えてください

もしくは、この質問に答えてください。

istringstreamのオブジェクトに、文字列を代入(?)するとき、
istringstream is(string("abc"));
のように初期化ではなくて、あとから代入することはできますか?
やり方を教えてください。
493デフォルトの名無しさん:2008/07/29(火) 10:18:55
>>491
いつの間にそうなったんだ…

関数呼び出し時に初回判定が入るんじゃあパフォーマンス
に悪影響があるだろうが。

func(){
static int a = 100;
}

は昔どおり初回判定なんか入らないよな?
494デフォルトの名無しさん:2008/07/29(火) 10:34:42
>>493
昔から変わってないよ。その int の例でも、関数内で値の変更があったり、
ポインタや参照を外に渡してしまっている場合は初回判定が必要になるでしょ。
495デフォルトの名無しさん:2008/07/29(火) 10:35:44
昔どおりも何も、単に最適化で判定が消えてるだけだろ
496デフォルトの名無しさん:2008/07/29(火) 10:37:38
>>495>>493
497デフォルトの名無しさん:2008/07/29(火) 10:38:57
>>492
istringstream ではなくて stringstream を使ってみては?
498デフォルトの名無しさん:2008/07/29(火) 10:41:57
499デフォルトの名無しさん:2008/07/29(火) 10:42:21
定数での初期化なら、初回実行時でなくmainの前にされたりするよ。
その辺の最適化は処理系定義。

引数で初期化したら、まず確実に判定が入る。
500デフォルトの名無しさん:2008/07/29(火) 11:07:28
std::wofstreamを使ってテキストに書き込む時自動的にファイルの
頭にBOMを追加してくるみたいなものって存在しますか?

自分で先に書くのが普通でしょうか?

自分でFF FE をファイルと開いて書き込んでから
wofstreamを使うと先に書き込んだ2バイトが消されてしまい途方にくれて
おります・・・・
501デフォルトの名無しさん:2008/07/29(火) 11:09:44
自分で先に書くのが普通。
502デフォルトの名無しさん:2008/07/29(火) 11:22:18
std:ios::app だっけ?
503デフォルトの名無しさん:2008/07/29(火) 11:22:48
>>499
つまり、関数内のstatic変数の初期値が定数じゃない限り、初回確認用のフラグもstatic領域に用意されるわけだな。
504デフォルトの名無しさん:2008/07/29(火) 11:36:53
>>501-502
std:ios::appでBOMが残せましたmありがとうございます!
505デフォルトの名無しさん:2008/07/29(火) 11:43:28
>>494
一連のレスは理解できるのだが、

> int の例でも、関数内で値の変更があったり、
>ポインタや参照を外に渡してしまっている場合は初回判定が必要

これが分からん。

プログラムロード時にaが100になるでしょ。それで、関数内で
値の変更があったり、 ポインタや参照を外に渡してしまっている
場合はどうして初回判定が必要になるの?
506デフォルトの名無しさん:2008/07/29(火) 11:48:26
>>505
例えばこんなケース。

int func(int n)
{
static int a = n;
return a;
}

int main()
{
for (int a = 2; a <= 5; ++a) {
printf("%d, %d\n", a, func(a));
}
return 0;
}
507494:2008/07/29(火) 12:23:54
>>505
変数宣言通過時に初期化されるんなら初回判定が必要かと思ったんだけど、
プログラム起動時に初期化してもいいみたい。

ってことで >494 は間違いで、初回判定が必要になるのは初期値が定数式じゃないときね。


ごめんよ >>506
508デフォルトの名無しさん:2008/07/29(火) 14:13:54
横から失礼します
ファイル中のN個の値で、配列a[N]を作りたいんですが
うまいやり方が思いつかないので、どなたか教えていただけませんか?
509デフォルトの名無しさん:2008/07/29(火) 14:15:51
>>508
mallocの使い方を聞いてるのか?
510デフォルトの名無しさん:2008/07/29(火) 14:19:20
malloc( new? ) を使えば出来るんですね。やってみます。
511デフォルトの名無しさん:2008/07/29(火) 16:37:39
std::vector<型> a(N);でもよいぞ
512デフォルトの名無しさん:2008/07/29(火) 18:48:40
ワイマール憲法を構造体で記述せよ
という夏休みの課題が出たのですが、何から始めていいかさっぱりわかりません・・・・。
だれか御助けを・・・・。
513デフォルトの名無しさん:2008/07/29(火) 18:49:31
イクイク、ワイマール憲法
514デフォルトの名無しさん:2008/07/29(火) 19:32:11
struct kenpoo {
int Y;
int O;
};
515デフォルトの名無しさん:2008/07/29(火) 20:45:26
>>512
残念ですが、その課題を出した先生は脳に異常をきたしています・・・。
まともな対話は不可能でしょう。課題の提出は諦めるほかないでしょう。
516デフォルトの名無しさん:2008/07/29(火) 21:39:36
みんなイクイク、ベルサイユ条約
517デフォルトの名無しさん:2008/07/29(火) 22:07:51
ああ、1919か
518デフォルトの名無しさん:2008/07/29(火) 22:26:11
class hoge{
private:
std::list<int> foo;
public:
void setfoo(std::list<int> foo){
this->foo.clear();
std::list<int>::iterator itr;
for(itr=foo.begin();itr!=foo.end();itr++)
this->foo.push_back(*itr);
}
std::list<int> getfoo() const{
return foo;
}
};

int main(){
hoge hoge0;
std::list<hoge> hogehoge;

std::list<int> tmp;
tmp.push_back(1);
tmp.push_back(2);
hoge0.setfoo(tmp);
std::list<int>::iterator tmpitr = hoge0.getfoo().begin();
hogehoge.push_back(hoge0);
std::list<int>::iterator itr = (*hogehoge.begin()).getfoo().begin();
std::cout << *itr << "," << *(++itr);
}
このコードで、最後に"1,2"と表示されて欲しいところが、"0,0"となってしまいます。
どこが悪いのかがわからず困っています。よろしければ教えていただけないでしょうか…。
519デフォルトの名無しさん:2008/07/29(火) 22:30:32
ほう、それがワイマール憲法か。なるほど
520デフォルトの名無しさん:2008/07/29(火) 22:34:42
getfooの戻り値であるhoge::fooの一時コピーが次の文に移る間までに破棄されてしまうからと、
ひとつの式の中でitrを代入と参照の両方してるから
521518:2008/07/29(火) 23:03:49
>>520
ありがとうございます。
最後にcoutするところで、itrが無効化してしまってるということでしょうか。
一時コピーが破棄されるタイミングがイマイチわかりません。
たびたびすいません…。
522デフォルトの名無しさん:2008/07/29(火) 23:15:52
>>521
完全式の終わりで破棄される
523デフォルトの名無しさん:2008/07/29(火) 23:39:25
だれか、C++のえろい人
百聞は一見にしかずだから
>>518のコードを希望通りに動くように修正汁!

すまん、俺C++わからんから><
524デフォルトの名無しさん:2008/07/29(火) 23:44:32
getfoo()の戻り値を参照型に換えたら?
525デフォルトの名無しさん:2008/07/30(水) 00:02:27
C言語勉強のためにプログラムを作成しました。
が、printf("hello")の時点で壁にぶちあたりました。
正しくコードを入れたはずですが、実行して表示されるのは、
2chアップローダ:http://www-2ch.net:8080/up/download/1217343270379299.ZNkHRl
です。exeと、badが同時に出現するのは何故?さらHELLOが表示されていないのは何故?
「苦しんで覚えるC言語」を参考にやってみたのですが、いきなり苦しいです。
神様助けてください。。。
コンパイラ:Borland C++ Compiler
エディタ:CPad for Borland C++Compiler
526デフォルトの名無しさん:2008/07/30(水) 00:17:17
さらに
std::cout << *itr << ",";
std::cout << *++itr;
と二行に分けると動く。

その理由は、((std::cout.operator<<(*itr)).operator<<(",")).operator<<(*++itr)
というようにちょっと考えるとインクリメント演算子は後から適用されるように思えるが、
インクリメント演算子は副作用完了点に達するまでのどの段階で働いても
構わない事になっているからである。

もっと言えば>>518の動作は未定義である。
527デフォルトの名無しさん:2008/07/30(水) 00:18:11
>>525
なんで start ってするの?compile したのは a.exe とかじゃない?

ところでその本には int main(void) 推奨なの?
528デフォルトの名無しさん:2008/07/30(水) 00:19:57
start.cをコンパイルしたからstart.exeなんじゃないの
529デフォルトの名無しさん:2008/07/30(水) 00:21:51
start.cなんだからbcc32ならstart.exe吐いてくれるはず

まあたぶん./startってやったら動くんじゃない
530デフォルトの名無しさん:2008/07/30(水) 00:24:31
例えば

#include <iostream>
int main()
{
int i = 1;
std::cout << i << ' ' << ++i << std::endl;
}

のようなプログラムは "1 2" と出力しそうであるが、実際は未定義動作であり、
無理矢理動かすと大抵のコンパイラでは直感に反して"2 2"と表示されるのも
同じ理由による。
531デフォルトの名無しさん:2008/07/30(水) 00:25:04
読み返して言葉足らずでした。補います。
printf("hello");では上記URLのようにexeと、badが同時に出現し、また何も表記が無い状態でしたが
printf("hello\n");では「HELLO」が改行ありで表記されました。
また、printf("%d",100); printf("円\n");では改行ありで「100円」が表記されました。
私の見解では、ただ単に参考にした構文が間違っている(\nが必要だが書かれていなかっただけ)
のだと思いますが。。。意見を聞かせてください。
532デフォルトの名無しさん:2008/07/30(水) 00:26:06
コマンドプロンプトにstartってコマンドあるから
start.exeはまずくない?
533デフォルトの名無しさん:2008/07/30(水) 00:26:14
>>531
printfのあとに
fflush();つけたらどうなるかな?
534533:2008/07/30(水) 00:27:06
いろいろ間違えたごめん忘れてください
535デフォルトの名無しさん:2008/07/30(水) 00:27:24
(なぁなぁ、badって何?)
536デフォルトの名無しさん:2008/07/30(水) 00:32:52
あ、startじゃぁまずいですか^^;
aに変えました。そしたらbatのみになりました。
参考元URL:http://homepage3.nifty.com/mmgames/c_guide/index.html
しかも、printf("hello");で改行なし「hello」が表示されました。
お騒がせ申し訳ありません。m(--)m参考元さんも申し訳ありません。m(--)m
537デフォルトの名無しさん:2008/07/30(水) 00:42:51
unixでtestという実行ファイルを作ってハマった当時の俺
538デフォルトの名無しさん:2008/07/30(水) 00:44:24
あるある
うん。あるある
539デフォルトの名無しさん:2008/07/30(水) 00:44:46
batやらbadやら恥ずかしいことばかり書き込んでしまいました。
セキュリティーホールがあれば入りたいです。
startをaに変更すると、
http://www-2ch.net:8080/up/download/1217345861729515.WpasSs
な感じになりました。これで夜も安心して眠れます。

>>527 startにしたのは無知だからでした。「手始めにスタート」のつもりでした。
この本というかサイトではそうでした。他のサイトを見てみると他の記述もありましたが、
最初に見たこのサイトの記述で貫こうと思います。

>>532 決定的な回答ありがとうございます。小鳥の1歩ほど前進することができました。
終わりなきC言語を心ゆくまで堪能したいと思います。親切にしてくださってありがとうございます。

>>534 いっしょにセキュリティーホールに入りませんか。

>>535 完全に撃ち間違いです。申し訳ありま栓。

540デフォルトの名無しさん:2008/07/30(水) 02:16:56
すいません質問です。
ソラリスでは使えてたのですが、Linuxだとエラーが出てしまってgoogle検索したのですがいい対応策が見つかりません。

newとdeleteは演算子なのですが、

string * aaa;
というのを.hで宣言し
.ccにて
コンストラクタでNULLクリア
main処理にて値を入れる場合と入れない場合があるのですが、
値を入れない場合に、
デストiラクタでaaaをdeleteしようとすると、落ちてしまいます。
SolarisからLinuxに入れ替えようとしているので、Solarisでは通るのにLinuxでは通らないという事はあるのでしょうか。
簡単にプログラムの例を
classで、
string * aaa;  を宣言しておき、

コンストラクタで、aaaをNULL初期化します。
mainルーチンで、aaaにファイルから文字列を取得するのですが、
該当しない場合はaaaはNULLのままとなっています。
デストラクタで、
if(aaa){
delete aaa;
}
とやっているのですが、そこで落ちてしまいます。
よろしければアドバイスお願いします。





541デフォルトの名無しさん:2008/07/30(水) 02:19:23
コンパイラはgccです
542デフォルトの名無しさん:2008/07/30(水) 02:19:37
VC++を使用しているのですが、
char ItemObject[1024];
ItemObject = "TEST";
listBox->Items->Add(ItemObject);
とするとコンパイルできません。
プログラミング初心者で、どうすればいいのか分からず困っています。
どなたか、助けて下さい。よろしくお願いします。
543デフォルトの名無しさん:2008/07/30(水) 02:20:01
delete演算子は対象のポインタが 0 の時は何もしないで
戻るようになっている。

従って if文は不要。原因は他の所にあるのではないか。
544デフォルトの名無しさん:2008/07/30(水) 02:23:19
>>542
listBox->Items->Add( gcnew System::String(ItemObject) )

はじめから System::Stringを使え。
それより、このスレはC++/CLIはOKなのかな?C++/CLIはC++とは別物だから明記しておくように。
545デフォルトの名無しさん:2008/07/30(水) 02:28:22
>>543
>>delete演算子は対象のポインタが 0 の時は何もしないで
>>戻るようになっている。
これは知ってはいたのですが、チェックしてしまうクセがついてしまっています。

>>従って if文は不要。原因は他の所にあるのではないか。
やはり原因は他にあるのですかね。
Soralisで通っててLinuxでは通らないので、規格の違いかと思い質問させてもらいました。
(LinuxはSoralisと比べて厳しいので
もうちょっと調べてみます。

アドバイスありがとうございます。
546デフォルトの名無しさん:2008/07/30(水) 02:29:17
>>540
クラスも無いのにコンストラクタとか言ってるのがおかしい。ソース晒せ。
547デフォルトの名無しさん:2008/07/30(水) 02:33:41
memsetでクリアしてたりする?
548デフォルトの名無しさん:2008/07/30(水) 02:39:30
>>546
class hoge{
string * aaa;
}

mainでaaaに文字列を取得
(ない場合は取得しない

hoge::hogeでaaaにはNULLを設定

oge::~hogeで
if(aaa){
delete aaa;
}

としています。

>>547
>>memsetでクリアしてたりする?
memsetはやっていないですね。

文字列取得にはc_str()を使用しています。
549デフォルトの名無しさん:2008/07/30(水) 02:42:52
>>548
hoge にデストラクタもコンストラクタもねーじゃねーか。
ソースを省くな。問題が再現する完全なコードを貼れ。
550デフォルトの名無しさん:2008/07/30(水) 02:51:20
>>549
すいません、完全なコードを張る事ができないので省略してました。
何かしらヒントでもあればと思い質問しました。
SoralisとLinuxの互換性がまだ完全に把握できていないので
分かる人がいればと思い。

もうちょっと自分で調べてみます。解決したら役に立つかわかりませんが書き込みます。
551デフォルトの名無しさん:2008/07/30(水) 02:59:06
>>550
問題が再現する最小のコードを作ってもらわないと、エスパーでもなけりゃわからない。
OS間の互換性に原因があると思ってるようだが、どうせ違う。

そういうコード作るのは相談のためでもあるが、基本的な調査の方法でもあるんで、
たいていは作ってる間に自分で気づくんだけどな。
552デフォルトの名無しさん:2008/07/30(水) 03:10:02
全くのあてずっぽうだが、
hogeが意図せずコピーコンストラクタでコピーされてて、
2箇所でaaaがdeleteされているとかないだろうか。
deleteしたばかりで領域が再利用されていない場合に
2回目のdeleteでもエラーにならない処理系は存在する。
Soralisが落ちない処理系で、linuxが落ちる処理系だとすると・・
553デフォルトの名無しさん:2008/07/30(水) 03:19:04
>>552
一応gdbでも処理追ってみたのでコンストラクタが2度通ってる事はないみたいです。
554デフォルトの名無しさん:2008/07/30(水) 03:23:12
privateでコピーコンストラクタをきってみたら?
デフォルトのコピーコンストラクタが使われているなら、
普通のコンストラクタは通らないよ。

stringがstl::stringだったらポインタで持つ意味があるのかは検討したほうがいいな。
555デフォルトの名無しさん:2008/07/30(水) 03:26:42
>>554
なるほどprivateもありですね。試してみます。
stringはstd::stringです。
556デフォルトの名無しさん:2008/07/30(水) 03:49:12
OSが違ったら通らないではなくて、Solarisではたまたまエラーが
出なくてLinuxではしっかりチェックされて落ちるってオチだろうな。

多分ソースにバグがある。
557デフォルトの名無しさん:2008/07/30(水) 03:58:01
>>556
その可能性大ですね。
Solarisはチェックが甘いからたまたま通ってただけな気がします。
時間あるから作り直そうかな。他にもありそうですし。

元々作った人が逃げて改修まかされて困ったもんです。

558デフォルトの名無しさん:2008/07/30(水) 03:58:37
Solarisはdeleteした領域を触っても落ちないからね。
559デフォルトの名無しさん:2008/07/30(水) 04:07:31
linux gcc(4.0)は2回deleteでセグメンテーション違反を確認。
vc++2008は落ちないのを確認。
560デフォルトの名無しさん:2008/07/30(水) 04:19:15
#include <string>

int main()
{
std::string* str = new std::string;

delete str;
delete str;
}

BCC5.9.3(C++Builder2007付属品)+CodeGuardで次のログ出力。

Error 00004. 0x100630 (スレッド 0x0C24):
解放済みメモリの アクセス : アドレス 0x00D743E0+16 から 4
バイトを参照しました。.
| C:\Program Files\CodeGear\RAD Studio\5.0\Include\dinkumware\xstring line 1757:
| else if (_BUF_SIZE <= _Myres)
| { // copy any leftovers to small buffer and deallocate
|> _Elem *_Ptr = _Bx._Ptr;
| if (0 < _Newsize)
| _Traits::copy(_Bx._Buf, _Ptr, _Newsize);
呼び出し履歴:
0x00401477(=double_delete1.exe:0x01:000477) C:\Program Files\CodeGear\RAD Studio\5.0\Include\dinkumware\xstring#1757
0x004012FE(=double_delete1.exe:0x01:0002FE) C:\Program Files\CodeGear\RAD Studio\5.0\Include\dinkumware\xstring#561
0x00401205(=double_delete1.exe:0x01:000205) double_delete1.cpp#8
0x328876DE(=CC3280MT.DLL:0x01:0866DE)
561デフォルトの名無しさん:2008/07/30(水) 04:22:07
他にも解放済みリソースを参照したとのエラーログがたくさん
出力されましたがあまりに長いため省略します。

Linuxにはこの手のデバッガはありませんか?
562>>542:2008/07/30(水) 04:24:09
お礼を忘れてました。すみません。
お答えを下さった方、助かりました。どうもありがとうございました。
563デフォルトの名無しさん:2008/07/30(水) 04:29:09
>>560
gdbがある
zeroとかなんとかそういう感じのもあった気がする
564デフォルトの名無しさん:2008/07/30(水) 04:33:14
>>561
前述したようにdeleteの2重はありませんが、
そのプログラムで
str に NULLを代入し、str に対して delete を行うとLinuxでは落ちてしまいます。

デバッガはgdbが標準でついてるはずなのでそれで可能です。
gdbのコマンドとしては、
落ちた時のcoraファイルを取得し
gdb main.o coreファイル名
で、デバッグ可能です。
main.oはLM名です。

gdbのプロンプトに変わりますので、そこから解析は可能ではあります。
565デフォルトの名無しさん:2008/07/30(水) 04:46:46
>>564
素朴な疑問なんだけどNULLと0が違うんかもしれんね。
0を代入してdeleteしてみ。
566デフォルトの名無しさん:2008/07/30(水) 06:19:13
いやいや。C++でそれはありえないでそ
567デフォルトの名無しさん:2008/07/30(水) 06:20:03
つーか、gccのバージョンはいくつよ?
568デフォルトの名無しさん:2008/07/30(水) 06:33:15
>>564 の書き込みが正しいとすれば
ユーザー定義のNULLが存在するのかもしれない
調べてみては?
569デフォルトの名無しさん:2008/07/30(水) 09:27:14
>>564
#include <string>
int main() { std::string* str = new std::string; str = NULL; delete str; delete str; }

↑これで落ちるってこと?
ヌルポインタの delete で落ちるんならコンパイラが腐ってる。
>567 も挙げてるけど、コンパイラは何?
570デフォルトの名無しさん:2008/07/30(水) 09:47:33
>>564
再現する最小ソースが作れないほどの規模らしいから

str に NULLを代入し、

*ここに何かいっぱい処理がある

str に対して delete を行うとLinuxでは落ちてしまいます。
571デフォルトの名無しさん:2008/07/30(水) 09:55:49
strに副作用のある部分を二分探査でブレークポイントなりデバッグ出力なりを掛けてどこが問題か探すんだ。
572デフォルトの名無しさん:2008/07/30(水) 11:45:50
例外処理のサンプルソースを見てたのですが、

#include <iostream>
using namespace std;

int main()
{
int num;
cout << "1から9までの数を入力してください\n";
cin >> num;

try{
if(num <=0){
throw "0以下を入力しました\n";
}
if(num >=10){
throw "10以上を入力しました\n";
}
cout << num << "です\n";
}

catch(char* err){
cout << "エラー:" << err << '\n';
return 1;
}
return 0;
}

catchブロックのreturn 1というのは異常に終了したから1を返すという意味ですか? 試しに0で実行しても同じ結果だったので気になりました。
573デフォルトの名無しさん:2008/07/30(水) 11:54:09
>>572
実行した後に、何が返ったのか調べることができる。
どうやって調べるかは実行したシェルによる。
調べなきゃ何もかわらない。
574デフォルトの名無しさん:2008/07/30(水) 11:55:33
>>572
お使いのコマンドインタプリタに終了ステータスが渡されています。
その値を見ることができれば、0だったり1だったりするのが判ることでしょう。
575デフォルトの名無しさん:2008/07/30(水) 12:01:45
>>573 >>574
ありがとうございます
今日も良い一日を
576デフォルトの名無しさん:2008/07/30(水) 16:36:05
#include <stdio.h>
#include <stdlib.h>
#include <tchar.h>

int main()
{
FILE *fp;
wchar_t buf[16] = {0};

if(_wfopen_s(&fp, _T("hoge.txt"), _T("w, ccs=UTF-8"))) exit(1);
fputwc(_T('あ'), fp);
fputwc(_T('イ'), fp);
fputwc(_T('菟'), fp);
fclose(fp);

if(_wfopen_s(&fp, _T("hoge.txt"), _T("r"))) exit(1);
for(int i = 0; i < 3; i++)
{
buf[i] = fgetwc(fp);
}
fclose(fp);

wprintf(_T("%s"), buf);

return 0;
}
このようにUTF-8で入出力すると、出力はうまくいくのですが入力で文字化けが起きてしまいます
どうすればいいのでしょうか。環境依存のものですが、よろしくお願いします。
WindowsXP + VC2005です。
577デフォルトの名無しさん:2008/07/30(水) 16:38:19
_T("r, ccs=UTF-8")だったというオチ?
578デフォルトの名無しさん:2008/07/30(水) 16:40:37
どう化けるのさ。
入力したものの画面出力、じゃないの?
ロケール設定してみては。
579デフォルトの名無しさん:2008/07/30(水) 16:41:44
入力でもccs=UNICODEとccs=UTF-8で試しましたが駄目でした。
入力では文字コードのフラグがなくてもBOMで勝手に判断してくれるとのことなのですが……。
580デフォルトの名無しさん:2008/07/30(水) 16:43:00
>>578
ええ、コンソール出力したものが化けます。
そちらが問題なのでしょうか。
581デフォルトの名無しさん:2008/07/30(水) 16:43:12
wprintf(_T("%s"), buf);←ここがUTF-8じゃない
582デフォルトの名無しさん:2008/07/30(水) 16:54:38
ちょっとやってみたよ
"r, ccs=UTF-8" にして、 #include <locale.h> 追加して setlocale(LC_ALL, "japanese"); 追加したら出たよ。
583デフォルトの名無しさん:2008/07/30(水) 17:16:02
>>577-578,581-582
ありがとうございます。
setlocaleの使い方が分からなくて手間取りましたが無事出ました。
ということは入出力はちゃんと行われているんですね。
ロケールについて少し調べてみます。
584540:2008/07/30(水) 22:24:54
こんばんは。先日の者です。寝てあたますっきりしたところでもう一度処理全体を追ってみました。
簡略すると下記のようなソースになります。
@で、aaaの初期値にnull_stを代入しており、
その後ifを通らなかった場合に、
Aのdeleteで同じ箇所を2度行おうとし、落ちているみたいでした。

>>558さんの言う通りSolarisはdeleteした領域を触っても落ちないのですね。

解決策として、Bの記述を
null_st = NULL;
に変えようかと思うのですが、これは大丈夫なのでしょうか。
質問ばかりですみません。

main()
{
string* aaa;
string* null_st;
int cnt;

null_st = new string(""); // B
aaa = null_st; // @

// cntは別の所で操作されると思ってください。
if(cnt == 1)
{
aaa = new string("AAA");
}

delete null_st; // A
delete aaa; // A
}
585デフォルトの名無しさん:2008/07/30(水) 22:29:04
…だったら、null_stっていらなくね?
586デフォルトの名無しさん:2008/07/30(水) 22:34:35
std::stringをポインタで扱うのがそもそも間違い
587540:2008/07/30(水) 22:47:16
なるほど。
規模が結構大きくて全部改修するには手間がかかるので必要最低限だけを変えたいんですが、
string* null_st;
を消して、NULLにするだけで大丈夫ですかねぇ
588デフォルトの名無しさん:2008/07/30(水) 22:51:50
NULLじゃなくてカラ文字として扱いたいからそうしてるんだろ?どこかでヌルポにならないか。

aaa = new string("AAA"); のあと
aaa = new string("BBB"); 別の文字を代入することあったら、
"AAA"がメモリリークをおこしてるようなことはないだろうか。
589540:2008/07/30(水) 23:08:10
aaa = new string("AAA"); のあと
aaa = new string("BBB"); は、みたところありませんでした。
別の文字列を入れる場合は必ずdeleteが走る仕組みになってます。
590デフォルトの名無しさん:2008/07/30(水) 23:16:23
既存のソースを扱ってるなら可哀想だけど、
自分で書いたのなら、何故入門書なり入門サイトを見ずに書いたのかと・・・
591デフォルトの名無しさん:2008/07/30(水) 23:23:06
aaa = new string("AAA");の後に
aaa = new string("BBB");があったら、そらメモリリークですよ…

string* aaa = NULL;
if(cnt == 1){
aaa = new string("AAA");
}
if (aaa != NULL && aaa == "") {
//カラ文字の時の処理
}
if (aaa == NULL) {
// カラ文字どころか存在さえしない時の処理
}
delete aaa;
aaa = NULL; // ←これは別に必要ではない
592デフォルトの名無しさん:2008/07/30(水) 23:29:49
仮にaaa->empty()に加えてaaa == NULLという状況も扱いたいのなら、
素直にboost::optional使ったほうがいいと思う。
そうには思えないけど。
593デフォルトの名無しさん:2008/07/30(水) 23:30:52
生のメモリを扱えない他の高級言語から移ってきて
なんとなくメモリの扱いをわかった気になっているだけ、という匂いを感じる。
594591:2008/07/30(水) 23:33:17
え?おれ?
595デフォルトの名無しさん:2008/07/30(水) 23:33:42
だれだてめえ
596デフォルトの名無しさん:2008/07/30(水) 23:36:46
貴様らに名乗る名前はないっ!
597デフォルトの名無しさん:2008/07/31(木) 00:32:54
とりあえず、null_stで初期化してるとこをNULLで初期化するように変更しようと思います。
null_stは削除の方向で。
何か弊害ありそうでしたら教えてくださったら幸いです。
598デフォルトの名無しさん:2008/07/31(木) 00:44:14
if(*aaa == *null_st)とかif(*aaa != *null_st)があるかどうかかなぁ
あったらnull_strは消さない方がいいかも

あと590のカラ文字かの判定間違ってるわね
×if (aaa != NULL && aaa == "") {
○if (aaa != NULL && *aaa == "") {
599デフォルトの名無しさん:2008/07/31(木) 00:48:45
>>if(*aaa == *null_st)とかif(*aaa != *null_st)
この判定は試してませんでした。
その条件で大丈夫そうなら使ってみます。

このプログラム作った人がいたら、何を意図して作ったのか聞きたいんですが、
もういないので、聞くに聞けずここをいじったらまた別のが出てくるのではないかと
怖いんですよね。

ただでさえ、SolarisとLinuxのポーティングに苦労してるので・・

600デフォルトの名無しさん:2008/07/31(木) 01:39:40
ここでいいのか分からないんですが、マクロの質問です。
TCHARを使ったプログラムを書いていて、ヘッダ側とソース側で何故か
TCHARの定義が変わってしまい、
外部シンボル 〜が未解決
というエラーが出てしまいます。どうすればこれを回避できるのでしょうか?
601デフォルトの名無しさん:2008/07/31(木) 01:49:04
>>598
あ、判定にそのコードを使ってるかって事ですね。
それは使ってないです。

deleteする時にその条件使えばいいかなと思ったので、
>>599の解答になりました。
602デフォルトの名無しさん:2008/07/31(木) 02:02:03
ていうかさ、一口に「Linux」と言っても、いろいろあるわけよ。
gccのバージョンとかglibcのバージョンとか含めてね。
その辺のことすら示さないで、何が「挙動の違い」だか。
603デフォルトの名無しさん:2008/07/31(木) 02:24:28
gccのバージョンは3.4.6です

同じコード>>584
main()
{
string* aaa;
string* null_st;

null_st = new string("");
aaa = null_st;

delete null_st;
delete aaa
}

これで落ちると落ちないの違いがあるので挙動の違いじゃないんですか?
上記をコンパイルして実行してみるると、Solarisでは落ちます。Linuxでは落ちません。
挙動の違いじゃないなら何があるか逆に教えてください。
まだ互換性についても詳しくないので。
604デフォルトの名無しさん:2008/07/31(木) 02:25:18
すいません、逆でした。
Solarisでは落ちません。Linuxでは落ちます。
605デフォルトの名無しさん:2008/07/31(木) 02:27:42
そりゃ二重解放なんてしちゃ落ちてもしかたがなかろう
606デフォルトの名無しさん:2008/07/31(木) 02:55:50
だから、オレがやったんじゃないんだって・・
それを乗せ換え時に改修してるだけ
607デフォルトの名無しさん:2008/07/31(木) 04:48:54
>>584
昨夜からまだやってたのか
string* aaa; 
int cnt; 
aaa =  new string("");
if(cnt == 1) { 
  delete aaa;
  aaa = new string("AAA"); 

delete aaa;
608デフォルトの名無しさん:2008/07/31(木) 04:50:59
class foo {
  string aaa;
public:
  void set_aaa(const string& s) { aaa = s; }
  const string& get_aaa() { return aaa; }
};

// どうしても aaaをポインタにしたいならいろいろとやることが増える
class bar {
  string * aaa;
public:
  bar() { aaa = new string(""); }
  ~bar() { delete aaa; }
  void set_aaa(const string& s) { delete aaa; aaa = new string(s); }
  const string& get_aaa() { return *aaa; }
  bar(const bar& o) { aaa = new string(*o.aaa); }
  bar& operator=(const bar& o) { aaa = new string(*o.aaa); return *this; }
};
609デフォルトの名無しさん:2008/07/31(木) 08:45:11
あくまでも挙動の違いとして捉えたいなら「Solarisでは間違ったメモリ解放でも落ちないようになっている」か「>>603のコードではたまたま落ちてないだけ」としかいえない
言語のルールとしては明らかにおかしいんだから、さらに情報が欲しければそれぞれのスレで聞いたほうがよいのでは?

で、おかしいコードを改修してるんだよね
その改修ポイントのアドバイスとしては>>605はピンポイントで教えてくれてるんだからそんなにつっかからなくてもいいんじゃない
610デフォルトの名無しさん:2008/07/31(木) 09:28:49
つっかかってるわけじゃないんですが、すいません。
aaaはポインタじゃない方がいいんですね。
その場合どうするべきなのでしょう。

611デフォルトの名無しさん:2008/07/31(木) 09:33:24
同じオブジェクトを二度以上解放しないように改修すればすむことじゃないのか・・・
612デフォルトの名無しさん:2008/07/31(木) 09:34:08
もし本当に2重解放が原因と考えているのなら
全てのdeleteの直後にNULL代入のコードを追加して確認してみろ
613デフォルトの名無しさん:2008/07/31(木) 09:51:44
>>610
根本的なこと聞きたいんだけど、自分でプログラム組む時に
他人に質問しないでやり遂げられるくらいのレベルにはなってるの?

それともC/C++そのものがはじめて?

やり取り見てると何がしたいのかイマイチ意味不明。

確実なのは、Solarisのその落ちない状況が「たまたま」
だということで、「挙動の違い」というのが何を欲して
そういう風に言ってるのか分からない。

環境移してバグが表面化してるだけだから、解決方法は
ひとつしかない。二度開放するソースを直すしかない。
614デフォルトの名無しさん:2008/07/31(木) 10:10:22
>>610
>aaaはポインタじゃない方がいいんですね。 
>その場合どうするべきなのでしょう。 
string自体が文字ポインタとその先の文字配列を管理してるクラスなんだから
それをさらにポインタにしてそのインスタンスを管理するのは愚の骨頂。

>>584 のコードはこれだけになる。
main() { 
string aaa; 
int cnt = ... ; 
if(cnt == 1) { aaa = "AAA"; } 


つ〜か >>608 に解答があるじゃん。
615デフォルトの名無しさん:2008/07/31(木) 10:26:04
別に愚の骨頂と言うほどでもない。
616デフォルトの名無しさん:2008/07/31(木) 10:57:33
コピーをあんまり発生させたくないならポインタで引き回すのもありかな。
そのときはauto_ptrかshare_ptrを使おうぜ。

それなりにカオスな予感がするけど
std::auto_ptr<std::string> aaa(new std::string())
617デフォルトの名無しさん:2008/07/31(木) 12:47:28
改行と空白で区切って単語をvectorに格納したいです。教えて下さい。
ポインタと単語長を格納します。

class tango { public: char *p; int L; };

string str="abc defg hijkl mn\n opq \r\n rstu";
vector< tango > tng;



618デフォルトの名無しさん:2008/07/31(木) 13:04:36
宿題スレへ
619デフォルトの名無しさん:2008/07/31(木) 13:09:21
>>617
相談したいんなら、まず自分で書いたコードから。
620デフォルトの名無しさん:2008/07/31(木) 13:11:01
自分でできた

class tango { public: char *p; int L;
output(){string x(L+1,'\0'); memcpy(&x[0],p,L); cout<<x<<endl;}};
chk(char c){ return (c==0 || c==' ' || c=='\r' || c=='\n');}

int main() {
string str="abc defg hijkl mn\n opq \r\n rstu";
vector<tango> tng;
int i=0,L,sz=str.size();

for(;i<sz && chk(str[i]); i++);
while(i<sz){
for(L=1; L<sz && !chk(str[i+L]); L++);
tango x; x.p=&str[i]; x.L=L;
tng.push_back(x); i+=L;
for(;i<sz && chk(str[i]); i++);}
for(i=0;i<tng.size();i++) tng[i].output();}
621デフォルトの名無しさん:2008/07/31(木) 13:16:50
>>620
chk のループは、 string の find_first_of() と find_first_not_of() で置き換えるのがおすすめ。
622デフォルトの名無しさん:2008/07/31(木) 13:25:02
>>620
関数の戻り値省略しちゃダメ。

> output(){string x(L+1,'\0'); memcpy(&x[0],p,L); cout<<x<<endl;}};
これは
void output() const {cout<<string(p, L)<<endl;}};
でいい。
そもそも tango 自体が string でいいような気もするけど。
623デフォルトの名無しさん:2008/07/31(木) 13:27:21
sstream
624デフォルトの名無しさん:2008/07/31(木) 13:37:40
>>603
あくまで二重deleteにしか問題がない、ってことを他のソースコード
に一切手をつけないで確かめたいなら方法が無いこともないよ
625デフォルトの名無しさん:2008/07/31(木) 13:49:21
アドバイスありがとうございます。ソースが単純になりました。

class tango { public: char *p; int L; output(){cout<<string(p,L)<<endl;}};

int main() {
string str="abc defg hijkl mn\n opq \r\n rstu";
char dem[]=" \r\n";
vector<tango> tng;
int i=0,j;

while(1){
i=(int)str.find_first_not_of(dem,i);
j=(int)str.find_first_of(dem,i);
if(i==-1 || j==-1)break;
tango x; x.p=&str[i]; x.L=j-i;
tng.push_back(x); i+=j-i;}
for(i=0;i<tng.size();i++) tng[i].output();}
626デフォルトの名無しさん:2008/07/31(木) 13:52:10
>>622
stringだと参照ではなくコピーになるので元のメモリかファイルの量の倍になってしまいます。
Returnはエラーでない限りは省略してました。voidとかreturnはコンパイラに依存しますね
627デフォルトの名無しさん:2008/07/31(木) 14:00:37
>>626
C++ の標準規格では戻り値の省略はできない。
そのソースがコンパイルできることがコンパイラ依存。
「voidとかreturnはコンパイラに依存」こっちは意味不明。
628デフォルトの名無しさん:2008/07/31(木) 14:05:13
mainだけはありだろ?
629デフォルトの名無しさん:2008/07/31(木) 14:05:56
ごめん
630デフォルトの名無しさん:2008/07/31(木) 14:06:11
auto output(){ }
631デフォルトの名無しさん:2008/07/31(木) 14:17:14
>>626
tangoの中身をstringにすれば、625のコードで言うとこのstrが
空白区切りを終わった後は不要になるから、
何も考えずに倍のメモリを使うと決め付けるのは早計。
632デフォルトの名無しさん:2008/07/31(木) 14:29:37
でもファイルから読み込んだ場合、サイズが3Gとかあれば位置を記録した方がいいですよね
633デフォルトの名無しさん:2008/07/31(木) 14:31:45
3ギガオクテットちゃん?
634デフォルトの名無しさん:2008/07/31(木) 14:33:53
>>632
「サイズが3Gとかあれば」なんて事情があるなら、そのとおりだが、
その場合は元データを string に入れるのが間違いだろ。
istream で読んで、空白区切りの単語をそれぞれ string に入れたほうがいい。

まぁそんなことは正直どうでもよくて、読み手はエスパーじゃないんだから、
そういう特定の事情に依存する話をあたりまえのようにするなってことだ。
635デフォルトの名無しさん:2008/07/31(木) 18:12:39
ファイルの分割も作りました。 添削してもらえますか? ふたつに分けます。
あとstringのfind_first_ofはバイナリに対応出来ないので自作しました。

#include <string>
#include <iostream>
#include <vector>
#include <windows.h>
using namespace std;

string delimiter=" \r\n\0";
class tango { public: char *p; int L; output(){cout<<string(p,L)<<endl;}};
class file2array {
HANDLE fp, mp; char *p; DWORD sz;
public: file2array(string); ~file2array();
char* operator[](unsigned int); DWORD size();};

int find_of(file2array &p, string dem, int n){
unsigned int i,j;
for(i=n;i<p.size();i++){
for(j=0;j<dem.size(); j++)if(dem[j]==*p[i])return i;}
return -1;}

int find_not_of(file2array &p, string dem, int n){
unsigned int i,j,s;
for(i=n;i<p.size();i++){ s=0;
for(j=0;j<dem.size(); j++)if(dem[j]==*p[i])break; else s++;
if(s==dem.size())return i;}
return -1;}
636デフォルトの名無しさん:2008/07/31(木) 18:13:17
int main() {
file2array p("text.txt");
vector<tango> tng;
int i=0,j;
while(1){
i=find_not_of(p,delimiter,i);
if(i==-1)break;
j=find_of(p,delimiter,i);
if(j==-1)break;
tango x; x.p=p[i]; x.L=j-i;
tng.push_back(x); i+=j-i;}
for(i=0;i<tng.size();i++) tng[i].output();
return 1;}

file2array::file2array(string name){
fp=CreateFile(&name[0], GENERIC_READ, 0, 0, OPEN_EXISTING, 0, 0 );
if(fp==INVALID_HANDLE_VALUE){cout<<"file load err\n";return;}
sz=GetFileSize(fp, NULL);
mp=CreateFileMapping( fp, 0, PAGE_READONLY, 0, 0, "memmap" );
if( mp <= 0 ){cout<<"mapping err\n";return;}
p=(char*)MapViewOfFile( mp, FILE_MAP_READ, 0, 0, 0);}
file2array::~file2array(){ UnmapViewOfFile(p);CloseHandle( mp );CloseHandle( fp );}
char* file2array::operator[](unsigned int n){ return (p+n); }
DWORD file2array::size(){return sz;}
637デフォルトの名無しさん:2008/07/31(木) 18:29:20
質問なんですがメモリマップドファイルって効率良いですか?
順次アクセスしたときキャッシュにデータ乗るかと言う事です。
毎回HDDにアクセスしたら鈍いです。
自分でキャッシュ管理した方が確実で汎用性が上がりますか?
638デフォルトの名無しさん:2008/07/31(木) 18:33:23
>>637
share しなきゃ OS がよきに計らってくれると思う
639デフォルトの名無しさん:2008/07/31(木) 19:19:34
漠然とした質問で申し訳ないのですが、

あるオブジェクトのポインタを取得する関数が2通りあって、
どちらで取得したかによって、そのオブジェクトにアクセスできたり、
アクセスできずに落ちたりする現象が起こって困っています。

gdbで追っていくと、一方で取得したポインタは
(hoge *) 0x8f1d48   ←ポインタを返す関数で取得
もう一方で取得したポインタは
(hoge *&) @0x8f1b10: 0x8f1d48   ←ポインタのvectorを返す関数で取得後、at()で欲しい要素を取得
となっています。

同じアドレスを指しているのは間違いなさそうですが、
(hoge *)と(hoge *&)で異なった型?になっているようです。
これが原因かとも思うのですが、意味がよくわかりません。
もしお分かりになれば、教えていただけないでしょうか。
640639:2008/07/31(木) 19:29:03
元コードは大きすぎて載せられないのと、
再現する小さいコードが上手く作れない(再現しない)ので
コードがありません。申し訳ありません。
641デフォルトの名無しさん:2008/07/31(木) 19:32:18
ポインタが自動変数で、その参照を返してるとか?
642デフォルトの名無しさん:2008/07/31(木) 19:44:43
>再現する小さいコードが上手く作れない(再現しない)ので
バグはそこじゃないとこにいるんじゃね?
643デフォルトの名無しさん:2008/07/31(木) 19:45:44
独自のファイル形式のアイコンを変更させるプログラムを組みたいのですが、参考になるサイトはありますでしょうか。
検索しても実行ファイルのアイコンの変更が引っ掛かり、目的のページが見つからず困っています。
現在VC++2005(c++)で組んでいます。
644デフォルトの名無しさん:2008/07/31(木) 19:47:12
> 独自のファイル形式のアイコンを変更させる

何に変更させるの?
645デフォルトの名無しさん:2008/07/31(木) 19:50:12
>>644
何でもいいのですが、例えば.aaa形式のファイルのアイコンをこちらで用意してある32x32の真っ黒のアイコンに変えたりなど。
拡張子を表示させている人はいいのですが、ファイル名だけを表示している人にとって全て未定儀形式のアイコンだと分かりずらくて。
646デフォルトの名無しさん:2008/07/31(木) 19:52:54
>>643
検索ワード
関連付け アイコン レジストリ
647643:2008/07/31(木) 19:55:20
>>646
ありがとうございます。
レジストリ関連だったのですね。
648デフォルトの名無しさん:2008/07/31(木) 20:33:06
しかも、それC/C++に関係ないどころかプログラムも関係ないWindowsの機能
649デフォルトの名無しさん:2008/07/31(木) 21:06:25
まぁ、初心者のうちは切り分け出来なくてもしょうがないさ
650デフォルトの名無しさん:2008/07/31(木) 21:16:52
初心者で申し訳ないのですが、

人のプログラムを見てて、
new演算子を使用しているのにdelete演算子で開放していない場合としている場合がありました。
newとdeleteはセットで使うものだと参考書には書いてありましたが、
下のソースではp2をdeleteしていません。
deleteしなくてはいけない場合と、deleteしなくても良い場合があるのでしょうか?

hoge()
{
int *p1;
int i =0;
p1 = new int();
*p1 = 123;

〜中略

if(j==1)
{
int *p2;
p2 = new int();
{

delet p1;
}
651デフォルトの名無しさん:2008/07/31(木) 21:19:50
バグです
652デフォルトの名無しさん:2008/07/31(木) 21:33:32
他に渡してるとか

bar()
{
 int *p1 = new int;
 int *p2 = new int;
 foo(p2);
 delet p1;
}

foo(int *p)
{
// なんかいろいろ処理
delete p;
}
653デフォルトの名無しさん:2008/07/31(木) 21:43:34
ズボラさんが小物プログラムを書く場合、
どうせすぐ終了するからとdeleteをサボる場合があります。
でもホントはいけないことなので、必ずdeleteするクセをつけてください。
あと、他の関数に渡してその中でdeleteしている場合もありますが、
これも一ヵ月後の自分が見たときに混乱する原因になるだけなので控えるべきです。
654デフォルトの名無しさん:2008/07/31(木) 21:45:47
っていうか、生のポインタの使用をなるだけ控えるって方向性のほういいと思う。
655デフォルトの名無しさん:2008/07/31(木) 21:50:37
学習上ある程度触れておいたほうがいいんじゃね。
スマートポインタ使っても、中で何やってるか分かってないと詰まる事あるし。
656デフォルトの名無しさん:2008/07/31(木) 21:55:49
やはりdeleteは行うべきなのですね。
ありがとうございます。
657デフォルトの名無しさん:2008/07/31(木) 22:25:57
もう一つ質問なんですが、
deleteしなくてもプログラム的には大丈夫なのですか?
もちろん悪い事なんでしょうけど、実行しても落ちたりしないですし。
658デフォルトの名無しさん:2008/07/31(木) 22:32:45
>>657
メモリが解放されないこと以外何の問題も無い
プログラム終了時にはきちんと解放される(ごく一部のOSを除いて)
659デフォルトの名無しさん:2008/07/31(木) 22:34:53
いずれnewでメモリ確保できなくなってエラーになるんじゃん?
動かないプログラムって存在意義なくね?
660デフォルトの名無しさん:2008/07/31(木) 22:35:10
なるほど。ありがとうございます。
661デフォルトの名無しさん:2008/07/31(木) 22:37:00
見たのはLinux上で1秒もかからずに終わるプログラムなので
>>(ごく一部のOSを除いて)
これに該当しない限り大丈夫なわけですね。

>>659
ずっと動いているようなプログラムではまずいんですね。
662デフォルトの名無しさん:2008/07/31(木) 22:39:45
deleteしないと、デストラクタも呼ばれないな。
663デフォルトの名無しさん:2008/07/31(木) 22:50:55
ファイルポインタについて質問があります。

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

int main(void)
{
FILE *fp;
int i;
char buff[256];

memset( buff, 'Z', 256 );

if((fp = fopen( "nekoneko.txt", "w")) == NULL ) {
fprintf(stderr,"ファイルオープンエラー\n");
exit(EXIT_FAILURE);
}

printf("ファイル位置(書き込み前) = %ld\n",ftell(fp));

for (i=0; i<10; i++){
fputc('A',fp);
}
fputc('\0', fp);

printf("ファイル位置(書き込み後) = %ld\n",ftell(fp));

rewind(fp);

printf("ファイル位置(rewind後) = %ld\n",ftell(fp));
664デフォルトの名無しさん:2008/07/31(木) 22:52:35
663の続き

//   fclose( fp );
//   fp = fopen( "nekoneko.txt", "r");

    fread(buff, sizeof(char), 5, fp);
    *(buff + 5) = '\0';
    printf("%s \n", buff);

fclose(fp);

return(0);
}


○実行した結果 AAAAA とならずにあらかじめ初期化していた文字が表示されました。
Aを10個書き込んだのでrewind関数でファイルポインタを先頭に戻したので
ファイルの先頭からAを読み込めると思っていたのですがダメでした。
試しにfread関数の前で一度、ファイルをクローズ、読み込みモードで再度オープン
(コメントアウトした部分)を行えば AAAAA は表示されました

<質問>ファイルポインタの操作の仕方に問題があるのではないかと思いますが
    どうして上手くいかないのかが解りません。
    ファイルに書き込むことにより移動したファイルポインタを先頭に戻せば
    ファイルの最初から読み込めると思ったのですがこれは間違いでしょうか?

・作成したファイル(nekoneko.txt)にはAは10個書き込まれている
・rewind関数の代わりにfseek(fp,0L,SEEK_SET) またはfgetpos関数、fsetpos関数で
 ファイルポインタを先頭に戻しても駄目でした。
・ファイルから読み込むのにfread関数の他、fgets関数、fgetc関数を試したが
 駄目でした。
・Visual Studio 2005でコンパイルしました。
665デフォルトの名無しさん:2008/07/31(木) 22:56:54
fopen(・・・, "w")じゃなくてfopen(・・・, "rw")でやってみたらどうなる?
666デフォルトの名無しさん:2008/07/31(木) 23:04:52
"rw"なんてあったっけか・・・?

"w"で開くと読めない気がする
それをやりたいなら"a+"じゃないの?
667デフォルトの名無しさん:2008/07/31(木) 23:08:39
rwなんて無いか。
ファイルを開いて、読み書き同時にやることなんて、やったこと無かったな。
668663:2008/07/31(木) 23:13:01
>>665
コンパイルはOKでしたが実行時にエラーがでました

>>666
"a+"で実行したら上手く表示できました。

>>665>>666さん ありがとうございました。 
669デフォルトの名無しさん:2008/07/31(木) 23:14:24
読み書きしたいんならよく使うのは"r+"か"w+"だと思う
tmpfile()はモード"wb+"で一時ファイルを作成してくれる

"w+"だと既存のファイルがあるならtruncateして作成する
"r+"はファイルがない場合は失敗する

読み書きを切り替えるときは間にfseek()/fsetpos()を挟むように汁
670663:2008/07/31(木) 23:29:49
>>669
ファイルの読み書きの時には + が必要なんですね
今までそんなことも気に掛けずにC言語の勉強してきました。

ありがとうございました。
671デフォルトの名無しさん:2008/08/01(金) 00:08:47
初心者本では余り見かけないが、役に立つ課題。

空欄を埋めよ

モード  目的  ファイルがあるとき  ファイルがないとき
"r"   読み込み 開く
"w"   書き込み  開いて空にする
"a"   追記
"r+"  読み書き
"w+" 読み書き
"a+" 
672デフォルトの名無しさん:2008/08/01(金) 01:18:37
Linuxについて質問があります。
コンパイル時に↓のようなメッセージが出ます。

*** glibc detected *** free(): invalid pointer: アドレス ***

調べてみると、
GCCのバージョンがC++アプリケーションと互換がない場合に起こると。
InkscapeまたはそのC++ライブラリ(libstdc++, libsigc++, libglibmm および libgtkmm)を同じバージョンのGCCで再コンパイルすれば、問題は解消する。

いうのは分かったのですが、「ライブラリを同じバージョンのGCCで再コンパイルすれば」というのが分かりません。
ライブラリは提供されているものだと思っているのですが、自分でもコンパイルできるのでしょうか?

gccのバージョンは346で上記の記述されいるライブラリを使用していると思われるのは
libstdc++ なのですが、
libstdc++のバージョンは詳しくわかりません。
libstdc++.so.6だとは思うんですが・・

行き詰ってしまったので解決策あればよろしくお願いします。


673デフォルトの名無しさん:2008/08/01(金) 01:38:04
同一人物か。
674デフォルトの名無しさん:2008/08/01(金) 02:09:39
>>672
> ライブラリは提供されているものだと思っているのですが、自分でもコンパイルできるのでしょうか?

そうだよ。
675デフォルトの名無しさん:2008/08/01(金) 02:16:35
できるんだすね
どうやるのでしょうか
ソースがないと無理だと思ってました
良かったら教えてください。
676デフォルトの名無しさん:2008/08/01(金) 02:17:28
そうだよ。libstdc++のソースをダウンロードしてコンパイルする。
677デフォルトの名無しさん:2008/08/01(金) 02:17:40
>>675
ソースはあるのでがんばってください
678デフォルトの名無しさん:2008/08/01(金) 02:18:58
わかりました。
やってみます。
どうもです。
679デフォルトの名無しさん:2008/08/01(金) 04:55:13
こんばんわ。夜遅くにすみません
ネットゲームの解析等をやってみたいのですが
デバッガ?数値?C言語?な状態です・・・
一から勉強したいのですがどこで教わればいいのかわかりません
わかりやすい講座サイトを知ってる方いませんか?もしよければ教えて頂きたいです。
返事お待ちしてます
680デフォルトの名無しさん:2008/08/01(金) 04:55:52
スレ違いでしたら申し訳ないです。どのスレに行けばいいと一言頂いてもいいでしょうか…
681デフォルトの名無しさん:2008/08/01(金) 05:07:42
>>679
つまり規約違反なことして俺TUEEEしたいんですねわかります
682デフォルトの名無しさん:2008/08/01(金) 05:08:25
>>680
ネトゲのチーとスレでもいけば?そこにもなんの情報も無いけどw
683デフォルトの名無しさん:2008/08/01(金) 05:08:51
チート板ってあったかの〜
684デフォルトの名無しさん:2008/08/01(金) 05:34:13
・夏厨
・ネトゲ厨
・学生
・ルール違反
・文盲

三つ当てはまるだけで既に罪
五つも当てはめてるんじゃないぞコラ☆
685デフォルトの名無しさん:2008/08/01(金) 06:01:08
すみません。
visualc++2008
をつかってるんですがコンパイルするときに
1>.\Debug\cal.exe.intermediate.manifest : general error c1010070: Failed to load and parse the manifest. U_U!$kLdK
1>~[
って出ます。
これはなんなんでしょう。
スレ違いでしたらすみません。
686デフォルトの名無しさん:2008/08/01(金) 06:14:15
>>685
マニフェストが壊れてる。
それは新規に別のプロジェクトを作ってもでる?
687デフォルトの名無しさん:2008/08/01(金) 06:17:30
>>686
プロジェクトを新しく作り直したらでなくなりました。
ありがとうございました。
688デフォルトの名無しさん:2008/08/01(金) 09:11:56
Visual C++ 2008を使っています。
次のようなファイル名をドライブ名付きのフルパスに
変換する方法を教えてください。

%CommonProgramFiles%\test.dat


689デフォルトの名無しさん:2008/08/01(金) 09:13:53
Visual C++ 2008を使っています。
次のようなファイル名をドライブ名付きのフルパスに
変換する方法を教えてください。

%CommonProgramFiles%\test.dat


690デフォルトの名無しさん:2008/08/01(金) 09:15:29
>>672
それはライブラリの互換性を気にするより前に、アプリケーションプロ
グラムのバグを疑うべき。free()におかしなアドレスを渡しているって
いうのが直接の問題だから。

691デフォルトの名無しさん:2008/08/01(金) 09:21:26
Visual C++ 2008を使っています。
次のようなファイル名をドライブ名付きのフルパスに
変換する方法を教えてください。

%CommonProgramFiles%\test.dat
692デフォルトの名無しさん:2008/08/01(金) 09:22:31
Visual C++ 2008を使っています。
次のようなファイル名をドライブ名付きのフルパスに
変換する方法を教えてください。

%CommonProgramFiles%\test.dat
693デフォルトの名無しさん:2008/08/01(金) 09:23:59
>>690
いやいや、リンク時の話
.so と .a のバージョンが違うぜって事
694デフォルトの名無しさん:2008/08/01(金) 09:26:56
>>691
GetEnvironmentVariable
SHGetSpecialFolderPath
695540:2008/08/01(金) 09:49:50
おはようございます。
必要ないかもしれませんが、経過と報告を。
結局2重開放しないように修正しました。

>>598
まさしくその判定を使っているところがあったので、
削除はやめました。

>>613
初心者に毛が生えた程度です。

会社から2ch見れないので返事遅くなりすいません。
ありがとうございました。
696デフォルトの名無しさん:2008/08/01(金) 19:13:42
struct {
float x[100], z[100];
} formation;

void init()
{
float MIN=20;
int baseX[] = { 0, -1, 1, 0, -1, 1, 0, -1, 1, -2, 2, -2, 2, -2, 2, -2, -1, 0, 1, 2, -2, -1, 0, 1, 2 };
int baseZ[] = { 0, 0, 0, -1, -1, -1, 1, 1, 1, 0, 0, -1, -1, 1, 1, -2, -2, -2, -2, -2, 2, 2, 2, 2, 2 };

for(int i = 0; i < 25; i++)
{
formation.x[i] = baseX[i] * MIN;
formation.z[i] = baseZ[i] * MIN;
}
}

int main()
{
init();
return 0;
}

実行するとエラーが出て、その原因がわかりません。文法がおかしいのでしょうか? VC++2008です

>.\main.c(11) : error C2143: 構文エラー : ';' が '型' の前にありません。
1>.\main.c(11) : error C2065: 'i' : 定義されていない識別子です。
1>.\main.c(12) : error C2143: 構文エラー : ';' が '{' の前にありません。
1>.\main.c(13) : error C2065: 'i' : 定義されていない識別子です。
1>.\main.c(14) : error C2065: 'i' : 定義されていない識別子です。
697デフォルトの名無しさん:2008/08/01(金) 19:16:30
int i;
for(i = 0; i < 25; i++)
698デフォルトの名無しさん:2008/08/01(金) 19:16:54
>>696
main.c を main.cpp に変更してみては?
699デフォルトの名無しさん:2008/08/01(金) 19:17:46
もしくはc99モードでコンパイルしてみては?
700デフォルトの名無しさん:2008/08/01(金) 19:30:07
>>696
解決しました。たまにCやるとこれだ
701デフォルトの名無しさん:2008/08/01(金) 21:53:03
(質問)
同じ配列を表すのに下記のように違う書き方があります。
書き方によって処理の速度に違いなど出てくるのでしょうか?

int a[100] = { 1, 2, 3, 4, 5,・・・・,100 };
int *po;
int cnt;

po = a + 10;

(1)
for( cnt = 10 ; cnt < 100 ; cnt++ ){
   printf( " %d", a[ cnt ] );
}           ^^^^^^^

(2)
for( cnt = 10 ; cnt < 100 ; cnt++ ){
   printf( " %d", *(a + cnt) );
}           ^^^^^^^^^

(3)
for( cnt = 10 ; cnt < 100 ; cnt++ ){
   printf( " %d", *(po++) );
}           ^^^^^^^
702デフォルトの名無しさん:2008/08/01(金) 21:55:55
>>701
出る場合もあるし出ない場合もある
個々のコンパイラの出来による
703デフォルトの名無しさん:2008/08/01(金) 21:57:37
>>701
それを気にしないといけない状況ではないと思う
704デフォルトの名無しさん:2008/08/01(金) 22:11:03
実測すればいい。
705デフォルトの名無しさん:2008/08/01(金) 22:16:30
>>702
>>703

書き方によって処理の速度に違いがあるのなら
その書き方を意識して勉強していこうと思っていましたが
コ、コ、コンパイラとかそんなもん全然手が出せないので
地道に勉強していきます。

ありがとうございました。
706デフォルトの名無しさん:2008/08/01(金) 22:22:57
>>705
基本は、読みやすさ優先でOK
707デフォルトの名無しさん:2008/08/01(金) 23:00:39
>>701
VCだとデバッグ時に範囲チェックしてるせいで、[]より+の方が速かった。
708デフォルトの名無しさん:2008/08/01(金) 23:06:41
「デバッグ時の」性能差になんか意味あんの?
709デフォルトの名無しさん:2008/08/01(金) 23:19:50
最近のVCはデバッグ時とはいえ、配列の範囲チェックまでしてんのか?
と思って、逆アセンブルでコード見てみたけど、範囲チェックらしき処理はなかった。
710デフォルトの名無しさん:2008/08/01(金) 23:37:43
わざわざ逆アセンブルしなくても/FAオプションでよくね?
711デフォルトの名無しさん:2008/08/01(金) 23:40:31
>>710
見たい箇所にブレイクポイントを入れて、逆アセンブルのウインドウ開くだけだから、
わざわざって言うほど手間じゃないよ。
712デフォルトの名無しさん:2008/08/01(金) 23:45:21
そういうのがあるんだ。オールドタイプでスマヌ。
713デフォルトの名無しさん:2008/08/02(土) 00:09:36
配列だと、範囲外にトラップしかけているってだけじゃないの?
714デフォルトの名無しさん:2008/08/02(土) 00:26:08
ためしに、配列の範囲外に書き込んでみたら、ちゃんと実行時にエラーになったね。
int dmy1[10];
int tbl[100];
int dmy2[10];
tbl[100] = 1;

ポインタ経由で書き込んでみても同じエラーがでた。

int *p = tbl;
*(p+100) = 1;

どうやってトラップしてるんだろ。
715デフォルトの名無しさん:2008/08/02(土) 01:37:53
普通にデバッグレジスタ(DRn)使ってんだろ
716デフォルトの名無しさん:2008/08/02(土) 09:26:11
>>714
こんな感じの処理
int tbl[100]; int trap; // tbに続けて配置
trap = 121212; // 適当なmagic number
int *p = tbl; *(p+100) = 1;
if (trap != 121212) abort(); // 書き換わってないかチェック
なもんで
 *(p+110) = 1 と大きく跳ぶと引っかからない。
717デフォルトの名無しさん:2008/08/02(土) 11:36:13
>>709>>713>>715>>716
どれがあってるのか知らんが脳内が如何に多いのか分かってw
718デフォルトの名無しさん:2008/08/02(土) 11:56:28
>713と>715は推測しか書いてない件。
719デフォルトの名無しさん:2008/08/02(土) 12:47:16
CL /RTC1 でそのチェックがかかるはず。
VisualStudioを使ってるならデフォルトオンになってると思うよ。それで見解に差が出ている。
720デフォルトの名無しさん:2008/08/02(土) 13:01:51
>>718
「脳内が如何に多いのか」、多少無理のある誤読でもいいから、
とにかくわかりたくて仕方がないんだよ。
思春期の自尊心ってそういうもんでしょ?
721デフォルトの名無しさん:2008/08/02(土) 18:10:06
vector<string>の宣言時に一括して配列へ文字を
代入したいのですがそういう事は可能でしょうか?

javaとかだとこんな感じの事です。
var s1 = ["【", "】"];
散々調べたのですが見つからなくて。
722デフォルトの名無しさん:2008/08/02(土) 18:47:07
つ boost::assign
723デフォルトの名無しさん:2008/08/02(土) 18:48:22
>>721
C++0xまで待ってください。
724デフォルトの名無しさん:2008/08/03(日) 00:33:47
#include <iostream>
#include <string>

using namespace std;

int main()
{
string s1("【" "】");
cout << s1 << endl;
}

まあ、そういうことじゃないのは分かってるけど。
725724:2008/08/03(日) 00:36:05
あれ、なんか俺全然勘違いしてるorz orz orz
726デフォルトの名無しさん:2008/08/03(日) 00:38:52
vectorなくなてるww
727デフォルトの名無しさん:2008/08/03(日) 00:42:50
static const char * const initial_strings[] = {"boo", "foo", "woo",};
std::vector<std::string> > strings(initial_strings, sizeof(initial_strings) / sizeof(* initial_strings));
728デフォルトの名無しさん:2008/08/03(日) 00:46:27
>>717
709だけど、おれは別に脳内じゃないぞ。
関数を抜けるときにある範囲チェックを見逃してたけど、それは「範囲チェックで配列アクセスが遅くなる」って
話題とは関係ないから。
729デフォルトの名無しさん:2008/08/03(日) 08:36:49
気にするな、技術的考察が出来ない>>717はどうせ初心者だろう
730デフォルトの名無しさん:2008/08/03(日) 10:09:58
template<int N>
class Test
{
public:
  Test()
  {
    ???
  }
private:
  double values[N];
};

このvaluesをコンストラクタで全て0.0にしたいとき、
どんな方法が環境非依存でベター?
std::fill_n?
731デフォルトの名無しさん:2008/08/03(日) 10:18:06
1994年の参考書で
#include "stdio.h"
main( )
{
int ans=10;
printf("%d\n",ans);
retrun 0;
}
と書いてあったんですけど、これであってますか?
732デフォルトの名無しさん:2008/08/03(日) 10:37:12
もっと新しい本読もうぜ・・・
733デフォルトの名無しさん:2008/08/03(日) 10:37:15
>>730
パソコンなら問題ないんじゃね。
組込み機器で使おうと思ってるなら、標準ライブラリが存在しない場合も考慮して
for ( int i = 0; i<<N; i++ ) { values[i] = 0.0; }
とか?

>>731
あってるというのはどういう意味?
コンパイラを通してみれば、文法があってるかどうかは確認できるよ。
人間の目でチェックするより信頼できる。

動作があってるかどうか確かめるなら、実際にコンパイルして動かしてみるといいよ。
にちゃんねらの脳内で実行するより信頼できる。
734デフォルトの名無しさん:2008/08/03(日) 10:39:45
> #include "stdio.h"
> main( )
その参考書は捨てて良い。
735デフォルトの名無しさん:2008/08/03(日) 10:48:29
>>733
標準ライブラリとかは使えるとして、
なんか定番の初期化の方法とかあるのかな〜と思って。

tnks
736デフォルトの名無しさん:2008/08/03(日) 11:08:02
>>730
std::memset
737デフォルトの名無しさん:2008/08/03(日) 11:22:23
何度も文字の型変換をしなければならないのですが、最終的に文字化けしてしまいます。
何処がおかしいでしょうか?

font->draw()は画面に文字表示する関数です。
void draw(const wchar_t* text, Point position,Color color)

----------------------------------------------------------
std::string stdstr="自民党総裁";
const char* cstring = new char[256];
cstring = stdstr.c_str();
wchar_t wcstring[sizeof(cstring)*2];
MultiByteToWideChar(
CP_ACP, 0, cstring, strlen(cstring), wcstring, sizeof(wcstring));

font->draw(wcstring,Point(0,0,0,0),0xFFFF0000);
------------------------------------------------------------

↑では「自民党総裁 」の後ろに意味不明な文字が何個か表示されてしまいます。

単純に
font->draw(L"自民党総裁",Point(0,0,0,0),0xFFFF0000);
とした場合はきちんと表示されます。
738デフォルトの名無しさん:2008/08/03(日) 11:32:31
>const char* cstring = new char[256];
>cstring = stdstr.c_str();
char[256]分がメモリリーク

>MultiByteToWideChar(CP_ACP, 0, cstring,
>strlen(cstring)
'\0'が含まれないので、wcstringにもL'\0'が付かない
739デフォルトの名無しさん:2008/08/03(日) 11:34:29
>>738
ありがとうございます。

して、、どう書けばよろしいのでしょうか・・・
740デフォルトの名無しさん:2008/08/03(日) 11:38:28
>>737
wchar_t wcstring[sizeof(cstring)*2];

やりたいことはわかるけど、ポインタのサイズの2倍の個数の文字分
を確保するというコードになっている。(32btiプロセッサなら8文字)

"自民党総裁"は五文字だからたまたま納まっているけど、意図したい
のはそうじゃないでしょ?
741737:2008/08/03(日) 11:47:35
すいません、要するにどう書けばいいかをおしえてください。
その方が、どこがおかしかったか理由が類推しやすいので
理解しやすいです。

今のところ原因が全く分からないので
途中の理由を書かれても何のことか理解できないです;;
742デフォルトの名無しさん:2008/08/03(日) 11:48:54
ちなみに
wcstring[sizeof(cstring)*2] ='\0';
などと最後にくっつけてみましたが
変な文字が減ったものの完治はしませんでした。
743デフォルトの名無しさん:2008/08/03(日) 11:50:06
std::string stdstr = "自民党総裁";
wchar_t wcstring[256];
MultiByteToWideChar(CP_ACP, 0, stdstr.c_str(), -1, wcstring, sizeof(wcstring));
744デフォルトの名無しさん:2008/08/03(日) 11:51:27
>wcstring[sizeof(cstring)*2] ='\0';
おいおいメモリ壊してないか?
745デフォルトの名無しさん:2008/08/03(日) 11:54:44
>>736
ども
746デフォルトの名無しさん:2008/08/03(日) 11:58:18
>>743
ありがとうございます。
でも>>737の変換は全部通さないといけないので省略はできないのです。
実際のソースは関数に渡してたりしていて、そのせいでこの変換が必要なんです。

>>744
wchar_t wcstring[strlen(cstring)*2];
MultiByteToWideChar(
CP_ACP, 0, cstring, strlen(cstring), wcstring, sizeof(wcstring));
wcstring[strlen(cstring)*2] ='\0';

としたらコンパイルできませんでした;;
747デフォルトの名無しさん:2008/08/03(日) 12:03:05
あと、
const char* cstring = new char[256];
とか
wchar_t wcstring[256];
みたいに適当に決め打ちするのってよくないですよね?
748デフォルトの名無しさん:2008/08/03(日) 12:06:07
>全部通さないといけないので省略はできないのです。
言ってる意味がわからないんだが・・・
749デフォルトの名無しさん:2008/08/03(日) 12:08:16
>>748
std::string → const char* →wchar_t

という順序で必ず変換をしないといけないということです。
750デフォルトの名無しさん:2008/08/03(日) 12:08:56
>>747
もうちょっとC言語の基本しっかりしてから見直したほうがいいと思う。
確かに決めうちはよくないけど、それ以前に言語の動作が分かってない。
現状の知識でプログラム書いても正しいものにならないよ。
751デフォルトの名無しさん:2008/08/03(日) 12:09:31
const char* cstring = stdstr.c_str();

std::vector<wchar_t> wbuf(stdstr.length()*2+1);
MultiByteToWideChar( , , stdstr.c_str(), stdstr.length(), &wbuf[0], wbuf.size());
font->draw(&wbuf[0],Point(0,0,0,0),0xFFFF0000);
752デフォルトの名無しさん:2008/08/03(日) 12:11:38
>>749
意味がわからん・・・
>>743は実質、const char* → wchar_t なわけだが。
753デフォルトの名無しさん:2008/08/03(日) 12:12:25
ATLのCSringぐらいのものが標準に含まれて欲しい・・・・
754デフォルトの名無しさん:2008/08/03(日) 12:15:05
std::stringがあるだろ。CSringはstd::stringが無かった頃の遺産だよ。
755デフォルトの名無しさん:2008/08/03(日) 12:16:09
>>752
実際のソースは関数を跨いでるので、
その引数にあわせてあの順序で変換しながら渡さないといけないんです。
756デフォルトの名無しさん:2008/08/03(日) 12:16:58
>>749
宿題?
std::string → const char*なんて、c_str()でしかないと思うけど
757デフォルトの名無しさん:2008/08/03(日) 12:19:13
std::wstring mbstowcs(const std::string &s)
{
    int len = MultiByteToWideChar(CP_ACP, 0, s.data(), s.size(), 0, 0);
    std::vector<wchar_t> vec(len);
    MultiByteToWideChar(CP_ACP, 0, s.data(), s.size(), &vec[0], len);
    return std::wstring(vec.begin(), vec.end());
}
こんな感じかね
エラー処理省略してるが

標準C++の範囲でも一応エンコード変換できるっちゃできるけど
実装や信頼性がまちまちだったりするのがどうもな
758デフォルトの名無しさん:2008/08/03(日) 12:20:15
>>755
std::string str = "a";
const char* cs = str.c_str();
f(cs);

std::string str = "a";
f(str.c_str());
が同じってことは分かる?
759デフォルトの名無しさん:2008/08/03(日) 12:21:17
>>754
multibyte<->widechar変換の機能がほしいとか
CStringAのようにmbsをケアしてほしいとかいう意味じゃないの
760デフォルトの名無しさん:2008/08/03(日) 12:22:04
だから順序守ってください・・・
なんで質問の条件無視して話し勧めようとするんですか・・・
761デフォルトの名無しさん:2008/08/03(日) 12:23:30
>>760
ここはべつに君のための場所ではないからだよ
2chをカスタマーサポートセンターか何かだと思ってるのかい?
762デフォルトの名無しさん:2008/08/03(日) 12:23:34
その順序ってのが意味不明だからだろ
763デフォルトの名無しさん:2008/08/03(日) 12:25:30
要するに>>737の形は崩さずに少し弄って直したいってことだろ
764デフォルトの名無しさん:2008/08/03(日) 12:26:22
>>751で何が不満なんだよ?
自民党総裁とか書いてる時点で厨くせぇと思っていたが
765デフォルトの名無しさん:2008/08/03(日) 12:26:55
>>760
>>756>>758に答えてもらえます?

>>763
形は崩してないと思うよ。
>>743はちゃんとstd::string → const char* →wchar_tになってるし。
766デフォルトの名無しさん:2008/08/03(日) 12:27:43
あはははは
おもすれー
767デフォルトの名無しさん:2008/08/03(日) 12:34:10
std::string str = "a";
const char* cs = str.c_str();
f(cs);

std::string str = "a";
f(str.c_str());

これが同じなのは分かります。

ですがとりあえず下の順序を守ってください。
stdstrからスタートして、
const char*を必要最小限用意してそれに代入し、
最終的に必要最小限のwchar_tに出力してください。

std::string stdstr="自民党総裁";
const char* cstring = new char[256];
cstring = stdstr.c_str();
wchar_t wcstring[sizeof(cstring)*2];
MultiByteToWideChar(
CP_ACP, 0, cstring, strlen(cstring), wcstring, sizeof(wcstring));
768デフォルトの名無しさん:2008/08/03(日) 12:37:00
>>767
>これが同じなのは分かります。
下の文章・ソースを読む限り、分かってないです。
769デフォルトの名無しさん:2008/08/03(日) 12:41:56
ポインタとsizeofの勉強しておいでよ。
そのソースでどれだけバカなことやってるか分かるから。
770デフォルトの名無しさん:2008/08/03(日) 12:44:32
wchar_t wcstring[sizeof(cstring)*2];ってなんだ
771デフォルトの名無しさん:2008/08/03(日) 12:45:31
とりあえずなおったのでもういいです。
772デフォルトの名無しさん:2008/08/03(日) 12:47:15
773デフォルトの名無しさん:2008/08/03(日) 12:48:11
>>770
それを言う理由ってなんですか?
おかしいのは分かってるんで、だから質問してるわけですが。
774デフォルトの名無しさん:2008/08/03(日) 12:48:44
>>736
それはない。
775デフォルトの名無しさん:2008/08/03(日) 12:49:57
>>769
じゃあもうこのスレいりませんね。
どの質問も勉強して来いで終了ですね。
776デフォルトの名無しさん:2008/08/03(日) 12:51:04
先生にconst char*型の変数を使うよう言われたんだと予想
777デフォルトの名無しさん:2008/08/03(日) 12:51:04
何ムキになってる?カワイイw
778デフォルトの名無しさん:2008/08/03(日) 12:51:16
const char* cstring = new char[256];
cstring = stdstr.c_str();

ここでnew char[256]で確保した領域へのポインタは上書きされちゃってるけど
どうやってdeleteするつもりなんですか

newの意味ちゃんとわかってる?
779デフォルトの名無しさん:2008/08/03(日) 12:53:28
>>775
>>746の「そのせいでこの変換が必要なんです」のようなことを言うには、
知識が足りなさ過ぎるってことだよ
780デフォルトの名無しさん:2008/08/03(日) 12:53:57
もういいって言ってるんだからいいんじゃね?
781デフォルトの名無しさん:2008/08/03(日) 12:54:54
sizeof(cstring)っていくつになると思う?

256を期待してるなら間違いだぞ
4か8になるはずだ(環境による)
どうしてかはちゃんと調べることだ
782デフォルトの名無しさん:2008/08/03(日) 12:57:06
783デフォルトの名無しさん:2008/08/03(日) 12:57:25
>>775
人の話を聞いて理解を深めていこうとする人、ちゃんとコミュニケーションが取れる人には
ちゃんと教えてくれると思うよ。教えたがりも多いし。

説明はいいから俺の望む形で答え教えれ、なんていうからこんな流れになる。
784デフォルトの名無しさん:2008/08/03(日) 12:58:43
しかもその望む形が意味不明だしなw
785デフォルトの名無しさん:2008/08/03(日) 13:00:24
理解はしてます
どう書けばいいかだけ教えてくれればいいんです
バカにしないで下さい
786デフォルトの名無しさん:2008/08/03(日) 13:03:15
本人でない釣りの可能性に注意
787デフォルトの名無しさん:2008/08/03(日) 13:08:25
実際はこんな感じです。

クラスのメンバとしてstd::string stdstrを持ってます。
これにはstdstr = "自民党総裁";などと代入してあります。
で、引数がconst* charの関数にそれを渡します。
その際は、単純にstdstr.c_str()を使って渡します。
でその関数の中で文字表示font->draw()を実行しますが
それはwchar_tを要求します。

というわけでconst* charへはc_str()を使うだけでいいのは分かるのですが
質問するに際し、関数の受け渡しの部分を省略するために
>>737のように書いてみたわけです。

だから無駄なことをやってるのは分かるんですが、
もし実際書くとしたらどう書いたらいいのかということが気になります。

788デフォルトの名無しさん:2008/08/03(日) 13:12:05
>>787
質問する時はなるべく省略するべきではないこと、やむをえず省略した場合は、
その部分の都合は相手には伝わらないのが当然だということを理解してください。
789デフォルトの名無しさん:2008/08/03(日) 13:14:21
>>787
もう一度言うが
  std::string str = "a";
  const char* cs = str.c_str();
  f(cs);

  std::string str = "a";
  f(str.c_str());
は同じなんだよ。少しは考えろ。
790デフォルトの名無しさん:2008/08/03(日) 13:15:07
>>788
わけあってこういう事がしたい、って何度も何度も何度も何度も断った上で
お願いしてるんですから、別にそれ以上詮索する必要なんて無いですよね。
田代趣味があるならともかく。
791デフォルトの名無しさん:2008/08/03(日) 13:15:54
>>789
だからそれは知ってるって言ってるでしょ。
少しは考えろ。
792デフォルトの名無しさん:2008/08/03(日) 13:16:09
南風受けながら
793デフォルトの名無しさん:2008/08/03(日) 13:16:28
もう触るなよ。
794デフォルトの名無しさん:2008/08/03(日) 13:16:46
「とりあえずなおったからもういい」んじゃないのか
795デフォルトの名無しさん:2008/08/03(日) 13:17:37
めんどくせえな

std::string stdstr = "自民党総裁";
const char *cstring = stdstr.c_str();
wchar_t wcstring[256];
MultiByteToWideChar(CP_ACP, 0, cstring, -1, wcstring, sizeof(wcstring));

これでいいか?
>>743と意味は全く同じだがな
796デフォルトの名無しさん:2008/08/03(日) 13:18:07
>>789
いや、同じじゃないし。
前者はありがちなミス。
797デフォルトの名無しさん:2008/08/03(日) 13:18:13
>>787, >>791
  MultiByteToWideChar(CP_ACP, 0, stdstr.c_str(), -1, wcstring, sizeof(wcstring));

  const char* cstring = stdstr.c_str();
  MultiByteToWideChar(CP_ACP, 0, cstring, -1, wcstring, sizeof(wcstring));
にする理解力/応用力すら無いならプログラム書くのは諦めた方が良い。
798デフォルトの名無しさん:2008/08/03(日) 13:20:02
const char* cstring = new char[256];

これって何を意味しますか?
これは不正ですか?
799デフォルトの名無しさん:2008/08/03(日) 13:20:51
おまえらつられすぎw
800デフォルトの名無しさん:2008/08/03(日) 13:21:29
おまいらの優しさに全俺が泣いたwwww
801デフォルトの名無しさん:2008/08/03(日) 13:21:44
>>797
勝手に他人のやることを規定するなどという
思い上がりも甚だしいお前は人間諦めたほうがいいんじゃね。
802デフォルトの名無しさん:2008/08/03(日) 13:21:51
>>796
いや、同じだし。
おそらくc_str()の結果の有効期間を勘違いしてるよ。
803デフォルトの名無しさん:2008/08/03(日) 13:22:24
>>798
char型256個分の領域を確保して、そこへのポインタをcstringに納める
そこに文字列を入れたかったらstrcpy(cstring, stdstr.c_str())とかする
cstring = stdstr.c_str()はポインタを上書きするだけだからアウト
804デフォルトの名無しさん:2008/08/03(日) 13:23:01
>>801
ムキになんなw
805デフォルトの名無しさん:2008/08/03(日) 13:23:09
>>790
char 型で要素数256の配列の領域をnewで確保した。
cost char * 型の変数cstringを宣言・定義した。
その確保した領域の先頭アドレスをcstringの初期値として設定した。

その一文自体は不正ではない。
806デフォルトの名無しさん:2008/08/03(日) 13:24:07
>>803
なるほど。分かりました。
807デフォルトの名無しさん:2008/08/03(日) 13:25:36
うははははー
おもすれ
808デフォルトの名無しさん:2008/08/03(日) 13:26:06
>>803
>そこに文字列を入れたかったらstrcpy(cstring, stdstr.c_str())とかする

ならそういう書き方を教えてくれたらよかったのに・・・。
わざわざ領域確保して云々って条件で聞いてたんだから。
809デフォルトの名無しさん:2008/08/03(日) 13:26:20
初心者未満なのに何故あれほど強気なんだろうな
810デフォルトの名無しさん:2008/08/03(日) 13:27:22
宿題は宿題スレへ、としか・・・w
811デフォルトの名無しさん:2008/08/03(日) 13:28:49
strcpyすら知らないくせに教えてもらっといてケチ付けるなんてどんだけ傲慢なんだ
ゆとりこえー
812デフォルトの名無しさん:2008/08/03(日) 13:29:53
馬鹿すぎる
813デフォルトの名無しさん:2008/08/03(日) 13:30:26
>>811
strcpyで書けるならその書き方で教えればよかっただけじゃん。
かたくなに秘密にする意味って何www
814デフォルトの名無しさん:2008/08/03(日) 13:30:48
>>802
仕様書再確認しちまったじゃねぇか!
やっぱ違うぞ。
815デフォルトの名無しさん:2008/08/03(日) 13:32:52
>>813
「const char*の領域を新たに確保すること」という条件が付いた課題で無い限り、
>>737,>>787にstrcpyを使うのは馬鹿でしかないから。
816デフォルトの名無しさん:2008/08/03(日) 13:35:58
どうでもいいけど使った後はちゃんとdelete[] cstringしろよ
delete cstringじゃないからな
817デフォルトの名無しさん:2008/08/03(日) 13:37:49
それ以前にconst char*じゃstrcpyのdstにできない
何のためにconst付けてんの
818デフォルトの名無しさん:2008/08/03(日) 13:38:20
>>814
ごめんおしえて
>>789の上と下どう違うの? 何か見落としてるのか…?
819デフォルトの名無しさん:2008/08/03(日) 13:39:24
>>814
何がどう違うんだよ・・。
str.c_str()の戻り値は、strの非constメンバ関数が呼ばれるまで有効だぞ。
820デフォルトの名無しさん:2008/08/03(日) 13:39:34
>>815
だから何度も何度も何度も何度も”あえて”そう書くとしたらって断り入れたのに。
821デフォルトの名無しさん:2008/08/03(日) 13:44:19
>>820
つまりお前の説明が下手過ぎたってことだ。
それから宿題なら最初からそう言え。
822デフォルトの名無しさん:2008/08/03(日) 13:45:14
>>820
const付けてる時点で中身変えるつもりないんだろ(とみんな理解したはずだ)
MultiByteToWideCharを呼ぶまでに中身が変わらないならnewだのstrcpyだのは全く必要ない

中身変えたいならconst消せよ
823デフォルトの名無しさん:2008/08/03(日) 13:45:44
本題よりも>>814の説明が聞きたいんだけど
824デフォルトの名無しさん:2008/08/03(日) 13:47:55
const char* cs = str.c_str();//※
f(cs);
※の時点でEOSが来てるからc_str()が作った一時オブジェクトが消えてるかもしれない

f(str.c_str());
fにc_str()の戻り値が渡されて、fの実行が終わってからEOSだからfの実行中は一時オブジェクトが生きてることが保証される

こうですかわかりません
c_strってstring内のメンバへのポインタ戻すだけなの?一時オブジェクト作るの?
前者なら>>819の言う通りだし後者なら上で書いた通りになると思うんだけど
825デフォルトの名無しさん:2008/08/03(日) 13:50:34
>>824
コンストラクタ/デストラクタを持たない型の値を
一時オブジェクトとは普通言いません。
826デフォルトの名無しさん:2008/08/03(日) 13:52:20
>c_strってstring内のメンバへのポインタ戻すだけなの?一時オブジェクト作るの?

どっちもありうる。
が、実際はポインタ返すだけの実装ばっか。
827デフォルトの名無しさん:2008/08/03(日) 13:52:35
一時オブジェクトは作らない。
828デフォルトの名無しさん:2008/08/03(日) 13:53:26
>>824
>819 の言うとおり、次の非 const メンバ関数を呼ぶまでの間有効なポインタを返す。
一時オブジェクトは作られない。

やっぱり >814 が何を言ってるのかわからない。
829デフォルトの名無しさん:2008/08/03(日) 13:53:54
仕様上はどっちとは書いてない。
でも一時オブジェクトを作るのだとしても非constメンバ関数が呼ばれるまで有効なようになってなきゃライブラリが規格違反ってこった。
830デフォルトの名無しさん:2008/08/03(日) 13:54:11
戻り値const char*でどうやって一時オブジェクト返すんだよ。
作れねぇよ。
831デフォルトの名無しさん:2008/08/03(日) 13:54:40
そうですね
char配列の一時オブジェクトなんか作れるわけないな。勘違いしてた
だったらstrの非constメンバ呼ばれるまでは大丈夫そうだけど
832デフォルトの名無しさん:2008/08/03(日) 13:56:50
>>830
一時オブジェクトを返すんじゃなくて、
stringが内部的に一時オブジェクトを作ってその中で確保した領域のポインタを返すことはありえる。
でも、そんなことはどっちでもいいよな。
833デフォルトの名無しさん:2008/08/03(日) 13:58:51
>>832
お前も要勉強だなw
それやったら f(str.c_str()); でf値が渡る前に
その一時オブジェクトはデストラクトされてるよ。
834デフォルトの名無しさん:2008/08/03(日) 13:59:05
std::stringの内部表現がC文字列ではない場合は、C文字列に格納し直してその先頭ポインタを返すという可能性がある。
(現存するstd::stringにそんな実装は無いかも知れないけど)
故にc_str()はthrow()ではない。

何で今更こんな話題で盛り上がってるのかと思ったが、>>814のおかげということが分かった。
835デフォルトの名無しさん:2008/08/03(日) 14:00:54
const_cast<char*>(str.c_str())[0] = 'a';とかやってもstrが無事であるようにとか
別に決められてるわけじゃないんだろ
836デフォルトの名無しさん:2008/08/03(日) 14:01:21
何このスレ…

初心者は歓迎だが、
質問のしかたも分からない馬鹿は帰れ
837デフォルトの名無しさん:2008/08/03(日) 14:02:13
>stringが内部的に一時オブジェクトを作ってその中で確保した領域のポインタを返すことはありえる。
仮にこうなるとすると、それが開放されるチャンスはどこにあるの?
838デフォルトの名無しさん:2008/08/03(日) 14:02:45
>>832
一時オブジェクト ≠ 一時的に存在するオブジェクト

一時オブジェクトは規格の用語なので他の意味に転用しないように
839デフォルトの名無しさん:2008/08/03(日) 14:03:03
>>836
回答の仕方も分からない馬鹿は帰れ
840デフォルトの名無しさん:2008/08/03(日) 14:04:09
>>837
次にc_strが呼ばれて作り直すときとか
string自体のデストラクタとかじゃないの
841デフォルトの名無しさん:2008/08/03(日) 14:05:04
>>834
それと戻り値の有効期間や一時オブジェクトの話は関係無いぞ。
その実装ならstringのメンバに保持しておく必要がある。
842デフォルトの名無しさん:2008/08/03(日) 14:06:21
>>840
それ一時オブジェクトじゃないよ
843デフォルトの名無しさん:2008/08/03(日) 14:07:40
>>839
質問あっての回答だろうw
エスパーじゃないんだからw
844デフォルトの名無しさん:2008/08/03(日) 14:10:41
>>837
実装を考えてみると、stringのメンバにcchar*戻値用のvectorとかchar*とか
あって、そこに確保して返すことになるんじゃないか。
解放タイミングはstringのデストラクト時で。
845デフォルトの名無しさん:2008/08/03(日) 14:11:43
一時オブジェクトってのは語弊があるね。
テンポラリオブジェクトとか読みかえれ
846デフォルトの名無しさん:2008/08/03(日) 14:12:22
>>845
どっちも同じで語弊があるのも同じ。
847デフォルトの名無しさん:2008/08/03(日) 14:13:44
語弊がない単語キボンヌ
848デフォルトの名無しさん:2008/08/03(日) 14:15:05
戻り値用のメンバ変数
849デフォルトの名無しさん:2008/08/03(日) 14:15:15
で、仮にそういう変な仮メンバを中に持ってる実装だとしても、単に先頭返すだけだとしても、
非constメンバ呼ばれるまでは有効なことには変わりないんじゃないの
850デフォルトの名無しさん:2008/08/03(日) 14:15:43
>>847
string 内部のオブジェクト。
851デフォルトの名無しさん:2008/08/03(日) 14:19:45
>>849
そうなんだけど一部の人が違うと言い張ってる。←いまここ
852デフォルトの名無しさん:2008/08/03(日) 14:26:58
>>814も仕様書確認してって言ってるから、
その仕様書書いた奴が元凶かと。

やはり仕様書としては「The C++ Programming Language」の
PDFを持っておくべき。

あと関係無いけどD&Eオヌヌメ
853デフォルトの名無しさん:2008/08/03(日) 14:41:47
なんという盛り上がり・・・
レス速度を見ただけでワクワクしてしまった
俺は間違いなく出遅れ
       
   / ̄\
  | ^o^ |  
   \_/
854デフォルトの名無しさん:2008/08/03(日) 14:54:16
規格書なんて普段よまんから読み方わかんねえ

Requires: The program shall not alter any of the values stored in the array.
Nor shall the program treat the returned value as a valid pointer value
after any subsequent call to a nonconst member function of
the class basic_string that designates the same object as this.

「nonconstなメンバ関数呼び出しのあとは返されたポインタをさわっちゃいかんよ」
とは書いてあるけど「それまでは大丈夫だよ」ともはっきり書いてないな
でも、この書き方だと大丈夫だと受け取っていいんだろな
855デフォルトの名無しさん:2008/08/03(日) 15:02:07
>>814が仕様書のどこを典拠にしてそう言っているのか聞きたいな
856デフォルトの名無しさん:2008/08/03(日) 15:21:13
やっぱりC#が最強だな
857デフォルトの名無しさん:2008/08/03(日) 15:22:17
スレ違い
858デフォルトの名無しさん:2008/08/03(日) 15:30:25
std::stringに"abccbaabc"という文字列が入っているとします。
このstringから"abc"を取り除く(つまり"cba"にする)には、どうやればいいですか?
859デフォルトの名無しさん:2008/08/03(日) 15:38:24
string& replace(string& s, const string& from, const string& to)
{
    string::size_type m = 0, n;
    while ((n = s.find(from, m)) != string::npos) {
        s.replace(n, from.size(), to);
        m = n + to.size();
    }
    return s;
}

こんなもんでいいと思うが
boost::regexでも使っとけ
860デフォルトの名無しさん:2008/08/03(日) 15:40:02
boost::algorithm::erase_all(s, "abc");
861858:2008/08/03(日) 15:49:44
>>859,860
どうもです。
STLの範囲だけでやろうとすると結構めんどくさいんですね。
erase_allがぴったりでした。
862デフォルトの名無しさん:2008/08/03(日) 15:51:37
>>814が言っていることは合ってる
863デフォルトの名無しさん:2008/08/03(日) 15:53:16
>>862
自演の予感。
864デフォルトの名無しさん:2008/08/03(日) 15:54:32
>>863
残念ながら違うんだなこれが
865デフォルトの名無しさん:2008/08/03(日) 15:55:03
すまんさっきからageっぱなしだった
866デフォルトの名無しさん:2008/08/03(日) 15:55:19
>>862が言っていることは間違ってる
867デフォルトの名無しさん:2008/08/03(日) 15:55:23
どっちが正しいんだよ!!!!!!!
868デフォルトの名無しさん:2008/08/03(日) 15:56:12
>>868が言っていることは間違ってる
869デフォルトの名無しさん:2008/08/03(日) 16:04:25
自虐的だな。
870デフォルトの名無しさん:2008/08/03(日) 16:04:43
やっぱりC#が最強だな
871デフォルトの名無しさん:2008/08/03(日) 16:07:02
俺が正しい。
872デフォルトの名無しさん:2008/08/03(日) 16:07:59
>>854が真理だろ
873デフォルトの名無しさん:2008/08/03(日) 16:08:50
>>872
自演の予感
874デフォルトの名無しさん:2008/08/03(日) 16:09:44
>>873
残念ながら違うんだなこれが
875デフォルトの名無しさん:2008/08/03(日) 16:10:45
すまんさっきからageっぱなしだった

こうですかわかりません><
876デフォルトの名無しさん:2008/08/03(日) 16:12:36
>>875
sageとるがな
877デフォルトの名無しさん:2008/08/03(日) 16:14:54
どっちが正しいんだよ!!!!!!!
878デフォルトの名無しさん:2008/08/03(日) 16:15:57
ここまで全部俺の自演。
879デフォルトの名無しさん:2008/08/03(日) 16:16:18
どっちって何と何か分からなくなったよ
880デフォルトの名無しさん:2008/08/03(日) 16:17:44
>>878
残念ながら違うんだなこれが
881デフォルトの名無しさん:2008/08/03(日) 16:18:51
>>878
残念ながら違うんだなこれが。
882デフォルトの名無しさん:2008/08/03(日) 18:21:10
>>730
VCならTest() : values() {}
で規定値で初期化されるみたい
883デフォルトの名無しさん:2008/08/03(日) 18:23:16
>>882
\すげぇ/
884デフォルトの名無しさん:2008/08/03(日) 18:27:14
ただしC4351が出る
885デフォルトの名無しさん:2008/08/03(日) 18:32:16
(「環境非依存で」って書いてあるのにね)
886デフォルトの名無しさん:2008/08/03(日) 19:01:51
#ifdef XXX
// Debug用コード
#else
// Release用コード
#endif

こんな感じでDebug用とRelease用をわけるときのXXXの部分に入るマクロが思い出せないです。
何か標準であったと記憶しているのですが何でしたっけ?
887デフォルトの名無しさん:2008/08/03(日) 19:04:24
VCだったらDEBUGとか_DEBUGとかかしら

コンパイルオプション見てみたらいいんじゃ
C/C++のプロパティで-D_DEBUGとか書いてあったら_DEBUG
888デフォルトの名無しさん:2008/08/03(日) 19:08:18
>>887
thx
コンパイラ依存なんですね。
環境はVC2008EEで、_DEBUGでした。
889デフォルトの名無しさん:2008/08/03(日) 19:18:09
>>886
標準で決められてるのは assert() の有効無効を切り替える NDEBUG 。
890886:2008/08/03(日) 19:48:17
>>889
あー標準にもやはりありましたか。
そっち使うことにします。
ありがとうございました。
891デフォルトの名無しさん:2008/08/03(日) 19:50:51
#include <stdio.h>
#include <winsock2.h>

int main() {
TCHAR str[1024];
WSADATA wsaData;

WSAStartup(2 , &wsaData);
printf("バージョン = %d.%d\n記述 = %s\n状態 = %s\n" ,
(BYTE)wsaData.wHighVersion , wsaData.wHighVersion >> 8 ,
wsaData.szDescription , wsaData.szSystemStatus
);
WSACleanup();
return 0;
}
超初心者です。丸写しのコピーです。VC++2008でwindowsアプリケーションで貼ったら4つエラーが出たのですが、プロジェクトの設定が悪いのでしょうか。
アドバイスお願いします。っていうかWinsockの質問はここで良いですか?スレ一覧にも無いようですが、人気が無いのでしょうか。
892デフォルトの名無しさん:2008/08/03(日) 20:06:33
エラーが出たときはエラーメッセージも貼った方が
他の環境使ってる人も答えてくれやすい

winsockもここでいいんじゃね?
俺ここで教えてもらったことあるよ
893デフォルトの名無しさん:2008/08/03(日) 20:09:10
どうせws2_32.libだろ
894デフォルトの名無しさん:2008/08/03(日) 20:13:23
WinMainにしたら1>c:\users\documents\visual studio 2008\projects\作る!\作る!.cpp(4) : error C2632: 'int' と 'int' の 2 つの型指定子のあ
このエラーだけに成りました。ws2_32.libについてはよくわかりません。
895デフォルトの名無しさん:2008/08/03(日) 20:13:39
プロジェクト右クリック−プロパティ
構成プロパティ−リンカ−入力
追加の依存ファイルにws2_32.libと書いてOK
もっかいビルド
896643:2008/08/03(日) 20:17:09
教えていただいた単語を組み合わせて色々調べてみましたが、結局各ユーザーによる手動設定の方法しか見つかりませんでした。
これをCやC++のプログラム中で実行することを解説したサイトは無いのでしょうか。
もしかして一般に公開できないほど価値のあることだったり・・・?
897デフォルトの名無しさん:2008/08/03(日) 20:17:35
delete this

ってできます?
今自分のいる足元を壊すみたいな。
898デフォルトの名無しさん:2008/08/03(日) 20:22:10
>>895
ありがとうございます。

899デフォルトの名無しさん:2008/08/03(日) 20:23:33
>>896
レジストリキーが分かってるなら
それをRegOpenKeyExとかRegSetValueExとかで追加したり変更したりはできるじゃん?
そういう意味じゃないのきゃ?

>>897
できる
900デフォルトの名無しさん:2008/08/03(日) 20:23:58
>>897
出来るよ。
901デフォルトの名無しさん:2008/08/03(日) 20:25:26
WindowアプリでWM_NCDESTROY受け取ったらdelete thisで自殺するような
コードはわりと見かけるな
902デフォルトの名無しさん:2008/08/03(日) 20:25:38
>>896
RegSetValueEx HKEY_CLASSES_ROOT DefaultIcon
903デフォルトの名無しさん:2008/08/03(日) 20:26:53
IUnknownの実装とかでもdelete thisは使う
904643:2008/08/03(日) 20:27:57
>>899,902
レスありがとうございます。
その関数の存在自体分からない状態でしたので、加えた上で改めて検索してみたら求めていたサイトが出てきました。
本当に助かります。
905デフォルトの名無しさん:2008/08/03(日) 20:30:28
delete thisは、以降にメンバに触らなければ問題無い。
ただし行儀悪いコードには違いない。
906デフォルトの名無しさん:2008/08/03(日) 20:44:16
パソコン甲子園2007予選問題7を解いたのですが、
練習問題に書かれていたサンプルは答えが出たのですが、
http://opct.ath.cx/に投稿すると、wrongと出てエラーです。
http://algorithms.blog55.fc2.com/blog-category-18.htmlに書かれていた
プログラムは正解ですので、自分のミスだと思いますが、
理由がまったく分かりません。
どなたか、教えていただけないでしょうか?
よろしくお願いします。
http://kansai2channeler.hp.infoseek.co.jp/cgi-bin/joyful/img/7585.txt
907デフォルトの名無しさん:2008/08/03(日) 21:20:34
よく分からんけど無意味にグローバル変数使ってるのと
int mainじゃないのがちょっと気持ち悪いと思った。
908897:2008/08/03(日) 21:30:49
>>899
>>900
>>905
ありがとうございます。

>>905
コードを手っ取り早く短くできるんで、どうかなと思ったんですが、
やっぱり行儀が悪いですね。
909デフォルトの名無しさん:2008/08/03(日) 21:51:32
>>906
何を聞きたいのか、わからない。
910デフォルトの名無しさん:2008/08/03(日) 22:22:11
delete thisはメモリ戦略を限定しちゃうからね
スタック配置不可、スマートポインタに格納不可、配置new不可、と。
911デフォルトの名無しさん:2008/08/04(月) 01:06:03
自殺クラスはそれをしないと手の届かないものに限定的に使うのであって、
自動変数にしたりスマポに入れたり配置newしたりするようなクラスには不要だろ。
912デフォルトの名無しさん:2008/08/04(月) 03:24:45
RAII技法に合わないのが致命的
913デフォルトの名無しさん:2008/08/04(月) 04:20:51
それをしないと手の届かないものってどんなのだろ?
いや、普通に思いつかなくて。
914デフォルトの名無しさん:2008/08/04(月) 08:39:44
>>913
ゲームのタスクシステムみたいなもので、リストでつながってる要素が
自殺したい時など。外部に消滅を管理する部分を設けなくても済む。
915デフォルトの名無しさん:2008/08/04(月) 17:05:47
C++で、
0からiまでの整数を入力させ、それ以外の数や、文字が入ったときはもう一回入力させることで、
確実に0からiまでの整数を戻す、以下のような感じの関数を作りたいんですが…

int nyuryoku(int i=1){
int a=0;
do{
cin>>a;
}while(a<0 || i<a);
return a;
}

数字以外の文字が入力されたときに固まったり無限ループになってしまいます。
istreamの問題だと思うのですが、対処が出来ません;;
どなたか教えてください
916デフォルトの名無しさん:2008/08/04(月) 17:13:26
>>915
そんな横着しないでgetlineしてパース汁
917デフォルトの名無しさん:2008/08/04(月) 17:48:01
918デフォルトの名無しさん:2008/08/04(月) 18:06:24
Cの勉強を始めたいのですが、入門書でバイブル的なものってあったリするんですかね?
それとも書店に売ってる本や雑誌の中から良さ気なのを適当に買ってきて始めても問題ないのでしょうか
スレチだったら申し訳ないです…
919デフォルトの名無しさん:2008/08/04(月) 18:20:56
本の最初のほうでmain関数というものが紹介されますが、
void main()
とか
void main(void)
と書いてある入門書は避けてください。

あとは第一印象でいいんじゃね。
920デフォルトの名無しさん:2008/08/04(月) 18:25:33

 俺は 「柴田望洋」 って人の本を図書館で数冊読んで勉強したよ.
 かなり判り易く書いてあったと思うけど,だいぶ昔の話だから今は
もっと良書があるかもね.
921デフォルトの名無しさん:2008/08/04(月) 18:34:29
main(argc, argv)
int argc;
char *argv[];
{

と書いてあったら古すぎ。K&R初版レベル。
922デフォルトの名無しさん:2008/08/04(月) 18:55:23
望洋はISO C++の本一冊も出してなかった気がするが。
今となっては絶対買ってはいけない地雷の一つじゃね
923デフォルトの名無しさん:2008/08/04(月) 21:01:47
マナ本はどうよ
924918:2008/08/04(月) 21:10:22
皆さんレスありがとうございます。
やっぱり特にこれがいいってのはあんまりないみたいですね。買う際の参考にさせてもらいます。
925デフォルトの名無しさん:2008/08/04(月) 21:28:38
>>921
今でも売ってるのかそんな本
926デフォルトの名無しさん:2008/08/04(月) 22:50:33
newで割り当てメモリサイズを、後から調べることってできないのでしょうか?

char *ptr = new char[10];
〜〜〜
//ptrのアドレス先に、いくらメモリを割り当てているか知りたい
927デフォルトの名無しさん:2008/08/04(月) 22:51:58
>>926
vector オススメ
928デフォルトの名無しさん:2008/08/04(月) 23:43:49
vectorみたいに割り当て時にサイズを記録するしか無いのでしょうか
929デフォルトの名無しさん:2008/08/04(月) 23:51:56
そうです。サイズを記録しておいて下さい。
慣れてくると、サイズでなくbeginとendで扱うようになるでしょう。
930デフォルトの名無しさん:2008/08/04(月) 23:55:42
たぶん無いんじゃないかなぁ
前にVCで探したけど見つからなかった

見つかったら教えてください
931デフォルトの名無しさん:2008/08/04(月) 23:58:41
うんこが苦いのはどうしてですか?
下痢便や軟便は特に超苦いです。
932デフォルトの名無しさん:2008/08/05(火) 00:02:48
苦い事自体初めて知りました、はい次
933デフォルトの名無しさん:2008/08/05(火) 00:10:16
>>926
空でないデストラクタのある型なら調べられない事もない場合があるが、
素直に vector 使っとこうぜ。

CString みたいなひねった記録のしかたをすることもできるが、
あれは可変長引数に渡せるようにするためのトリックであって
普通は必要になんない。
(まあ、空でないデストラクタのある型の場合
 自動的にそんな感じにするコンパイラもあるわけだが)
934デフォルトの名無しさん:2008/08/05(火) 00:14:31
HeapSize _msize
935デフォルトの名無しさん:2008/08/05(火) 00:21:08
>>934
感謝!
Win限定だけどあるのですね
936デフォルトの名無しさん:2008/08/05(火) 00:23:03
やっぱりCString最強だな
937デフォルトの名無しさん:2008/08/05(火) 00:38:48
>>935
いやそれさあ、newの返値に対して使えるの?

>_msize は,アドレスが block である割り当て済みのヒープブロックのサイズを返します。
>このブロックは,malloc,calloc,または realloc を使って割り当てられている必要があります。
>最初にブロックを割り当てるときに要求したバイト数より大きなサイズが返される場合があります。

しかもmallocに要求した数字より大きい数字が返ることがあるって。
まあ本人が良いなら良いかw
938デフォルトの名無しさん:2008/08/05(火) 02:14:34
>しかもmallocに要求した数字より大きい数字が返ることがあるって。

極めて普通に感じるけど。

9byte要求して
その環境でのalign(4byteや8byte)に適合するサイズに調整されて
12byteなり16byteなりを確保したのと全く同じように振舞った。
その結果、9ではなく12なり16なりの
要求した数字より大きい数字が返るってことだけど。
939デフォルトの名無しさん:2008/08/05(火) 02:27:13
多分そういう意味じゃないw
940デフォルトの名無しさん:2008/08/05(火) 02:29:33
>>926の時に10が帰ってくることを期待するなら使えないってことを言ってるんだろ。
想像力無さすぎる。
941デフォルトの名無しさん:2008/08/05(火) 10:05:16
>>926
char (&ptr)[10] = (char(&)[10]) new char[10];

で sizeof(ptr) は 10 になるがお友達にはなりたくない。
942デフォルトの名無しさん:2008/08/05(火) 10:26:59
胆汁は苦い
943デフォルトの名無しさん:2008/08/05(火) 10:33:57
だから下痢便も茶色くて苦い
944デフォルトの名無しさん:2008/08/05(火) 11:07:13
とんだ糞スレだわ
945デフォルトの名無しさん:2008/08/05(火) 11:10:23
夏ですなあ
946デフォルトの名無しさん:2008/08/05(火) 12:33:56

質問が無いと言うことは困っているプログラマもいない,平和でいいじゃないか
947デフォルトの名無しさん:2008/08/05(火) 13:28:12
>>937
配列のアクセス範囲が知りたいのじゃなく、使用してるメモリ量が知りたいので
>要求した数字より大きい数字が返ることがある
ってのは問題なし。

newで割り当てた全ての型に、正常に使えるのかは気になるところですが。
948デフォルトの名無しさん:2008/08/05(火) 13:42:47
いやそれ以前にnewに対して使えるんだ。
なんかnewの返り値をfreeに渡すみたいで気持ち悪いんだよね。
949デフォルトの名無しさん:2008/08/05(火) 13:46:53
まぁ、newのメモリ確保部分は大抵mallocだしね。
デバッグに使う分には良いんじゃない?
950デフォルトの名無しさん:2008/08/05(火) 13:57:44
関数の呼び出た回数を出力するにはどうしたらいいですか?
関数内でcount=0;とし、count++;で数えていくのはわかるのですが…
951デフォルトの名無しさん:2008/08/05(火) 13:58:54
>>950
そこまでわかって何が知りたいの・・・?
countをstaticにしておけばいいでしょ
952デフォルトの名無しさん:2008/08/05(火) 14:01:02
基本型ではない配列newに対して使える?
デストラクタ回す関係で、総サイズ以外に確保要素数もどこかに
書いてありそうなんだが…、コンパイラの実装依存か
953デフォルトの名無しさん:2008/08/05(火) 14:02:51
// 1
int count = 0;
void hoge(void) { ++count; }
// 2
void fuga(int * pCount) { ++(*pCount); }
// 3
void hage(void) { static int count = 0; ++count; printf("%d", count); }

さあ選べ。
954951:2008/08/05(火) 14:05:06
>>953
やさしいな
3がおすすめだけどな
955デフォルトの名無しさん:2008/08/05(火) 14:34:55
>>952
YOU、これ使っちゃいなYO
A* p = new A[3];
std::cout << reinterpret_cast<int*>(p)[-1] << std::endl;
delete[] p;

もちろんデバッグ目的限定で。
956デフォルトの名無しさん:2008/08/05(火) 14:43:41
>>955
VC++7.1とgcc3.4.4で試したけどどっちも駄目だった
それが動くのってどういう処理系?
957デフォルトの名無しさん:2008/08/05(火) 14:47:22
>>956
vc++8(2005)と記憶の中のvc++6。
958デフォルトの名無しさん:2008/08/05(火) 14:50:08
>>957
え?
#include <iostream>
int main()
{
    char *p = new char[10];
    std::cout << reinterpret_cast<int*>(p)[-1] << std::endl;
}
これ、俺のVC++8では、917968
とか印字されるけど。
959デフォルトの名無しさん:2008/08/05(火) 14:55:10
>>958
そりゃデストラクタ無い型なら出ないよ。
持つ必要無いから。
960デフォルトの名無しさん:2008/08/05(火) 14:55:47
ああ、そういう意味か。
理解した。
961デフォルトの名無しさん:2008/08/05(火) 15:10:05
ついでに。
デストラクタがある型の場合、
mallocで確保したメモリの先頭を要素数に使う(実装が多い)ので
HeapSize, _msizeにはそのアドレスを渡さないといけない。
ちなみにVC++のmallocは実質HeapAlloc。

A* p = new A[3];
HeapSize(GetProcessHeap(), 0, reinterpret_cast<int*>(p)-1)
_msize(reinterpret_cast<int*>(p)-1)
962デフォルトの名無しさん:2008/08/05(火) 16:45:39
WINAPIのシリアル通信のSetCommState()なんですが、ボーレート115200までは成功するんですが、230400でパラメータが正しくないと出ます。
COM1でこれ以上の速度はむりなんでしょうか?
963デフォルトの名無しさん:2008/08/05(火) 16:55:21
c/c++スレに書く内容じゃなくね?
964デフォルトの名無しさん:2008/08/05(火) 16:57:49
>>962
そもそもCBR_115200はあるけどCBR_230400なんてないんだが。
965デフォルトの名無しさん:2008/08/05(火) 17:09:04
スレ違い失礼しました
966デフォルトの名無しさん:2008/08/05(火) 23:35:37
stringに格納されている文字列を全部小文字にするには、tolower関数で1文字ずつ変換していくしかないのでしょうか?
967デフォルトの名無しさん:2008/08/05(火) 23:48:53
>>966
boost string_algoのto_lower/to_lower_copy使えばいい。
中でやっていることは結局1文字ずつstd::tolowerなんだけどね。
Boostが嫌なら自分でそういう関数を作るが由。
968966:2008/08/05(火) 23:51:23
>>967
thx
969966:2008/08/05(火) 23:52:06
>>967
thx
それ使って書きます。
970966:2008/08/05(火) 23:52:49
2重書き込みになってしまいました。ごめんなさい。
971デフォルトの名無しさん:2008/08/06(水) 02:05:13
std::mapのメンバ関数のfindですが、std::find_ifのように関数オブジェクトを使って比較することはできないのでしょうか?
972デフォルトの名無しさん:2008/08/06(水) 02:34:14
>>971
mapの仕組み上できない。
mapは構築時に指定された比較方法で内部的にソートしているので、
違う比較方法に対してはソートされていないvectorとかと同程度かそれ以下の効率しか出ない。
973デフォルトの名無しさん:2008/08/06(水) 02:38:18
例えばあるクラスAをnewでインスタンス化して、このインスタンスのメンバとして
newで生成したインスタンスBを保持していた場合、Aのインスタンスをdeleteする前に、
デストラクタなどでBをdeleteしなければなりませんか?
974デフォルトの名無しさん:2008/08/06(水) 02:49:21
>>972
なるほど。
でも、この関数オブジェクトって大小比較ですよね。
findの時はどんな仕組みになっているのでしょう?
まさかcomp(a, b)とcomp(b, a)の2回調べているのですか?
975デフォルトの名無しさん:2008/08/06(水) 03:08:36
operator <じゃなかったっけ
976デフォルトの名無しさん:2008/08/06(水) 03:09:34
>>974
そういわれれば二回比較しないと確定できませんね
977デフォルトの名無しさん:2008/08/06(水) 03:53:48
>>974
まぁ実装のアルゴリズム次第としか言いようがないんだが、
findの大抵の(効率の良い)実装ではoperator<だけでも(operator==を使わなくても)
検索に必要な比較回数の期待値は精々1回ぐらいしか増えないはず。

試しに二分探索をoperator<だけで書いてみるようなコードとか、
書かなくてもいいから頭の中でどうなるか考えてみると面白いかもね。

>>980
次スレよろ
978デフォルトの名無しさん:2008/08/06(水) 04:09:39
>>977
比較回数が1回程度しか増えないとは、うまいアルゴリズムがあるもんなんですね。
二分探索について調べてみます。
どうもありがとうございました。
979sage:2008/08/06(水) 18:18:37
new で確保したクラスオブジェクトをdeleteした際、
そのクラスオブジェクトの、newで実体を確保したデータメンバ(ポインタ)は、同時に自動的にdeleteされるのでしょうか??

ご教示頂けると幸いです。
980デフォルトの名無しさん:2008/08/06(水) 18:21:33
されますん
981デフォルトの名無しさん:2008/08/06(水) 18:22:03
>>979
メンバで保持してるポインタはdeleteされない。放置。
982デフォルトの名無しさん:2008/08/06(水) 18:22:32
確保したクラスがデストラクタでdeleteして無い限り、ポインタは解放されません。
983デフォルトの名無しさん:2008/08/06(水) 18:22:50
「されます」の変化形なのか「されません」の変化形なのかわかりません><
984979:2008/08/06(水) 18:23:40
ありがとうございます!
985デフォルトの名無しさん:2008/08/06(水) 18:24:05
struct hoge { fuga *pointer_; };

hoge *p = new hoge();
p->pointer_ = new fuga();
delete p;
とやったときに、自動で(見えないところで)
delete (p->pointer_);
も実行されるかってことだよね?

されません。

最近shared_ptrにべったりで、deleteなんて見てないや…。
986979:2008/08/06(水) 18:30:05
>>985
そんな感じです。
ありがとうございましたm(_ _)m
987デフォルトの名無しさん:2008/08/06(水) 19:12:53
言語そのものの質問じゃないのですが、WIN32APIとDirectXを
使用したソースをG++でMake可能でしょうか?
現在VC++Express使ってるんですが、将来的にMSがExpress配布
しなくなったときに、ソース(ほぼ)そのままでフリー環境に逃げれるのか気になって。
988デフォルトの名無しさん:2008/08/06(水) 19:20:08
心配しなくてもそのころにはコンパイラを気軽に買えるようになってるよ。
まあAPIやDirectXは結局はDLL呼び出しなんで、DLLが呼べればどこからでも使える。
ライブラリは互換性が無いので、gcc用に作るか作られたものをもってくればいい。
989デフォルトの名無しさん:2008/08/06(水) 19:20:16
将来Expressを配布しなくなっても、
今配布してるExpressが使えなくなるわけじゃないんだから、
DVDに焼いて大事に取っておけばいいんじゃない
990デフォルトの名無しさん:2008/08/06(水) 19:22:09
なるほど、可能なんですね。
取り越し苦労かもですけど、一安心しました。thx
991デフォルトの名無しさん:2008/08/06(水) 19:47:05
携帯の俺が言うのも何だけど、
そろそろ次スレ立てた方が良い。
992デフォルトの名無しさん:2008/08/06(水) 20:57:10
993デフォルトの名無しさん:2008/08/06(水) 20:58:16
>>987
インポートライブラリをreimpで変換するだけだす。
994デフォルトの名無しさん:2008/08/07(木) 01:45:11
>>987
DirectX9 関係では苦労します
DirectX10 は知りません

D3DX**** 系の関数を使用するときに注意が必要です
d3dx9.lib がスタティックライブラリなので vc 専用で g++ からは利用できません
g++ からは d3dx9_??.dll を使用できますが ?? 部分の数値が一致するものが対象のPCに存在しないと動きません

できれば vc を使ったほうが余計な苦労が無いと思います
995デフォルトの名無しさん:2008/08/07(木) 09:18:54
ifstreamで開いたファイルのサイズを取得するにはどうすればいいですか?
996デフォルトの名無しさん:2008/08/07(木) 10:51:29
std::ifstream f("test.txt", std::ios::binary);
f.seekg(0, std::ios::end);
std::size_t size = static_cast<std::size_t>(f.tellg());
997デフォルトの名無しさん:2008/08/07(木) 16:07:32
>>996
どうもです。
サイズ求めるだけなのに結構めんどくさいですね。
998デフォルトの名無しさん:2008/08/07(木) 16:21:19
stat()かそれに類する関数が大抵のシステムでは使えるはずだが、
標準ではないからな

boost::filesystemにはそのものズバリのfile_size()という関数があったと思う
999デフォルトの名無しさん:2008/08/07(木) 16:50:30
3行で面倒とか言ってたら何も作れんよ
1000デフォルトの名無しさん:2008/08/07(木) 16:55:23
面倒というか、ちょっと回りくどい感じはするね。
10011001
このスレッドは1000を超えました。
もう書けないので、新しいスレッドを立ててくださいです。。。