[表示 : 全て 最新50 1-99 101- 201- 301- 401- 501- 601- 701- 801- 901- 1001- 2chのread.cgiへ]
Update time : 05/29 13:41 / Filesize : 252 KB / Number-of Response : 1002
[このスレッドの書き込みを削除する]
[+板 最近立ったスレ&熱いスレ一覧 : +板 最近立ったスレ/記者別一覧] [類似スレッド一覧]


↑キャッシュ検索、類似スレ動作を修正しました、ご迷惑をお掛けしました

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



1 名前:デフォルトの名無しさん mailto:sage [2008/01/16(水) 15:14:51 ]
エスケープシーケンスやWin32APIなどの環境依存なものでもOK。
ただしその場合、質問者は必ず環境を書きましょう。
※sage禁止です(と代々スレに書いてありますが自己判断で)。
【前スレ】
【初心者歓迎】C/C++室 Ver.46【環境依存OK】
pc11.2ch.net/test/read.cgi/tech/1198755167/
【アップローダー】(質問が長い時はココ使うと便利)
kansai2channeler.hp.infoseek.co.jp/cgi-bin/joyful/joyful.htm

477 名前:デフォルトの名無しさん mailto:sage [2008/01/25(金) 11:56:10 ]
ワイルドカードはどんなのを?
そのままだとシェルが勝手に展開しない?

478 名前:デフォルトの名無しさん mailto:sage [2008/01/25(金) 11:57:55 ]
>>473
またお前か。あちこちおかしなプログラムなのは相変わらずだな。
最低でも、バッファオーバフローの可能性は排除しておけよ。

479 名前:473 [2008/01/25(金) 12:20:12 ]
>>477
*.csvとかですね。
そのままでは無理でした。

>>478
その件については、なんか知らんけどプログラムができあがりました。
あらかじめ指定されている仕様でしか作ったらいけないことになっておりまして、
どのようにすればそのようにできあがるのか悩まされている次第です。
一応さきほどのプログラムは作りましたが、io.hは無いそうで、_findnextも使えないですね。
こういうときそのヘッダファイルをダウンロードしてヘッダファイルがたくさんあるところに放りこめばいけますか

480 名前:デフォルトの名無しさん mailto:sage [2008/01/25(金) 12:37:23 ]
ヘッダだけ持ってきたって実装したライブラリが無きゃ無理だろ。
通常は、シェルが展開するんだが、、、opendir、readdir使って
正規表現で検索するとかしてみては

481 名前:473 [2008/01/25(金) 12:49:24 ]
>>480
ありがとうございます。
階層を一段間違えておりました。
普通に通りますね。よかった・・・

482 名前:デフォルトの名無しさん [2008/01/25(金) 13:31:29 ]
>>472
int main() {
double d = 3.55; // ここの数字を変更する
int n = d * 100;
cout << n << endl;
return 0;
}
でも上記プログラムでは、浮動小数点の規格上、

d = 0.55, 1.55, 8.55 =>それぞれ0.5500000....1, 1.55000...1, 8.55000...1
とかになるので、100倍しても減ったように見えたりしない。
d = 2.55, 3.55, 4.55, 5.55, 6.55, 7.55 =>それぞれ2.5499999...などとなるので、
100倍すると、(double)254.99999==>(int)254などとなってしまう。

と理解していたのですが、他の方も書いてくれてたように、Visual C++ 2008でやると
d=3.55の時、355と表示されました。(gccは354)





483 名前:デフォルトの名無しさん mailto:sage [2008/01/25(金) 17:29:42 ]
VC++がx86の80ビット浮動小数点数レジスタを使い回すからかと思ったけど、
一旦64ビットでメモリに書きだすように仕向けてもやっぱり355になるな。

484 名前:デフォルトの名無しさん mailto:sage [2008/01/25(金) 18:42:42 ]
関数に配列へのポインタへ渡してデータょ書いてもらう場合
std::vector buffer(1024);
hogefunc(&buffer[0]);
とかくのは違法ですか?

485 名前:デフォルトの名無しさん mailto:sage [2008/01/25(金) 18:47:47 ]
確保したバッファサイズをはみ出さないのなら問題ない



486 名前:デフォルトの名無しさん mailto:sage [2008/01/25(金) 19:08:51 ]
private:な物の位置調べて無理やり書き込むわけだが。

487 名前:デフォルトの名無しさん mailto:sage [2008/01/25(金) 19:19:56 ]
そういうことができるように、
vectorは生の配列同様、要素の連続性が保証されている。

488 名前:デフォルトの名無しさん mailto:sage [2008/01/25(金) 19:41:51 ]
ぬるぽ渡せば書かずに文字数返すくらいしてくれてもいいよな。
これみたいに。
ttp://msdn2.microsoft.com/ja-jp/library/k1f9b8cy(VS.80).aspx

489 名前:デフォルトの名無しさん mailto:sage [2008/01/25(金) 20:07:37 ]
>>488
Win32APIスレの誤爆か?

490 名前:デフォルトの名無しさん mailto:sage [2008/01/25(金) 20:51:13 ]
inline int nazo(void)
{
 return __LINE__;
}

呼び出すと戻ってくるのはどこのあれですか?

491 名前:デフォルトの名無しさん mailto:sage [2008/01/25(金) 20:52:04 ]
そこ

492 名前:デフォルトの名無しさん mailto:sage [2008/01/25(金) 20:59:02 ]
たぶん3

493 名前:デフォルトの名無しさん mailto:sage [2008/01/25(金) 21:01:39 ]
__LINE__やら__FILE__やら__func__はコンパイル時に埋め込まれる

494 名前:デフォルトの名無しさん mailto:sage [2008/01/25(金) 21:02:18 ]
__func__ マクロじゃなくて定数だったはず。

495 名前:デフォルトの名無しさん [2008/01/25(金) 21:09:16 ]
ik88
ectuo\
}{([8
]\@p :
dcdc
dcdcdcfvfv7qa11111111111111111111111111111111
mnbcadcfvghujk,ol9iikurf4ed333333333333333331W2E3TR4G56









496 名前:デフォルトの名無しさん mailto:sage [2008/01/25(金) 21:38:01 ]
きーけぼーどのいちばんうきえらをうつと

12w3e4rgt5h6789o0:^\
!"#$G%H&'()~*=~|

とにゅうりょくされます。
こしょうですか?

497 名前:デフォルトの名無しさん mailto:sage [2008/01/25(金) 21:41:14 ]
pepper

498 名前:デフォルトの名無しさん mailto:sage [2008/01/25(金) 21:55:26 ]
スキンラインの短絡

499 名前:デフォルトの名無しさん [2008/01/26(土) 03:17:03 ]
APIについての質問です。
Visual C++ Express 2008で英単語印刷ソフトを作っているのですが、
ウインドウに、ネットの検索欄のような入力欄を作ることは可能でしょうか?
それを使って単語の検索機能などを追加したいのですが・・・。
もしよろしければ教授ください。

500 名前:デフォルトの名無しさん mailto:sage [2008/01/26(土) 03:55:07 ]
VCスレかAPIスレ池。

501 名前:デフォルトの名無しさん [2008/01/26(土) 09:28:53 ]
>>482
gccでも、-msse2オプションをつけてコンパイルすると、355を返すバイナリを作れました。
でも、80ビットでも、52ビットでも、切り捨てになるから、どちらでも同じと思うんですが。
なんでだろう。

502 名前:デフォルトの名無しさん mailto:sage [2008/01/26(土) 11:06:09 ]
>>501
>482のコードだけなら、最適化で定数は事前(≒コンパイル時)計算されるから不思議ではない。

503 名前:デフォルトの名無しさん [2008/01/26(土) 20:29:17 ]
>>502
以下のコードでも、dに3.55を入力すると、表示は354になりますが、
-msse2でコンパイルすると355になりました。

int main(int ac, char **av)
{
double d;
cin >> d;
int n = d * 100;
cout << n << endl;
return 0;
}


504 名前:デフォルトの名無しさん mailto:sage [2008/01/26(土) 22:23:27 ]
確認のために聞きたいんです
関数テンプレートについてなんですが。

template<typename T>
void func(){
 hoge = new T();
}
func<HogeClass>();

つう書き方に、何か問題はありますか?
一応BCCでは動いてるようなんですが、
検索しても基本的に引数のために使われていて、
こういう書き方を見つけられなかったので不安なんですが。

505 名前:デフォルトの名無しさん mailto:sage [2008/01/26(土) 22:31:16 ]
>>504
全然問題ない。それができないならテンプレートの魅力が半減ですよ。



506 名前:デフォルトの名無しさん mailto:sage [2008/01/26(土) 22:48:00 ]
>>505
どうもです。こういう使い方はやっぱり便利なんですね。
でも、混乱もしそう。使いこなせるよう精進します。

507 名前:デフォルトの名無しさん mailto:sage [2008/01/26(土) 22:59:43 ]
>>503
手元のgccだとそのコードでも355になるよ。354になるときの値をprintf("%.20g", d * 100)で出してみて。

508 名前:デフォルトの名無しさん mailto:sage [2008/01/27(日) 03:55:57 ]
C++ で、perl の Data::Dumper みたいなことするのがあれば
教えてください。

509 名前:デフォルトの名無しさん mailto:sage [2008/01/27(日) 04:19:52 ]
テキストファイルをchar型に読み込んだ場合って改行があったら\nもちゃんと格納されるの?

510 名前:デフォルトの名無しさん mailto:sage [2008/01/27(日) 04:20:23 ]
読み込みかたによる。

511 名前:デフォルトの名無しさん mailto:sage [2008/01/27(日) 04:34:30 ]
ありがとう。読み方によるのね
できれば\nが格納される読み方の例教えていただきたい

512 名前:デフォルトの名無しさん mailto:sage [2008/01/27(日) 04:35:07 ]
fgets

513 名前:デフォルトの名無しさん mailto:sage [2008/01/27(日) 04:38:01 ]
ファイルの開き方も重要じゃないか

514 名前:デフォルトの名無しさん mailto:sage [2008/01/27(日) 04:42:08 ]
>>512
ありがとうございます。
fgetsって\nの手前までしか格納されないかと思ってたけど\nもちゃんと入るんですね
とりあえず色々試してみることにします

515 名前:デフォルトの名無しさん mailto:sage [2008/01/27(日) 04:44:40 ]
gets以外なら大体¥nもコピーする。fgets、fgetln、テキスト指向ですらないfreadも勿論。というかgetsは絶対使わない方が良い。
C++は…誰かお願い。



516 名前:デフォルトの名無しさん mailto:sage [2008/01/27(日) 07:26:38 ]
C++でWindowsでのDLL作成に関して質問です。
C++のクラスをエクスポートする場合、純粋仮想クラスを利用するようですが、この際、
多重継承は可能なのでしょうか。具体的には以下のようなことをしたいのです。
class IFoo{
public:
virtual void fooFunc() = 0;
};

class IBar: public IFoo{
public:
virtual void barFunc() = 0;
}

class CFooFunc{
public:
virtual void fooFunc(){ /*...*/ }
};

class CBarFunc{
public:
virtual void barFunc(){ /*...*/ }
};

class CExport: public IBar, CFooFunc, CBarFunc{
};

__declspec(dllexport) IBar* createIBar(){
return new CExport();
}
__declspec(dllexport) IBar* deleteIBar( IBar* p ){
delete p;
}

517 名前:デフォルトの名無しさん mailto:sage [2008/01/27(日) 09:21:25 ]
>>511
istream& istream::get(char& c)
istreambuf_iterator
unsetf ios::skipws and istream_iterator

518 名前:デフォルトの名無しさん mailto:sage [2008/01/27(日) 09:55:57 ]
>>516
DLL でクラスを公開したいなら COM

519 名前:デフォルトの名無しさん mailto:sage [2008/01/27(日) 12:57:31 ]
COM なんて使いにくいもんじゃなくて
__declspec(dllexport) と __declspec(dllimport) を使おうぜ。
DLL と EXE で自動的に切り替えるマクロもあったけど忘れた。

520 名前:デフォルトの名無しさん mailto:sage [2008/01/27(日) 14:30:07 ]
C++の初心者向けサイトを教えてください


521 名前:デフォルトの名無しさん mailto:sage [2008/01/27(日) 14:33:05 ]
#ifdef PROJECTNAME_EXPORTS
# define DLL_EXPORT __declspec(dllexport)
#else
# define DLL_EXPORT __declspec(dllimport)
#endif

522 名前:デフォルトの名無しさん mailto:sage [2008/01/27(日) 15:45:56 ]
そういうやつ、自分で作らなくてもあったと思うけど、
自分で作った方が細かい制御ができていいかもしれん。

523 名前:デフォルトの名無しさん mailto:sage [2008/01/27(日) 17:48:38 ]
dllexportは所詮同じヴァージョンのコンパイラ相手でしか使えないからね。

524 名前:デフォルトの名無しさん mailto:sage [2008/01/27(日) 18:11:43 ]
しかし、COM は COM で色々と不便だからなあ・・・。
IA ← A の機能強化版として IB と B を別途作るとして、

 IA
↑ ↑
IB A
↑ ↑
 B

こういう継承したいけど無理っしょ?
仮想継承がないから・・・。

525 名前:デフォルトの名無しさん mailto:sage [2008/01/27(日) 18:27:47 ]
ATLみたいに実装をテンプレートに分離すれば解決しない?



526 名前:デフォルトの名無しさん mailto:sage [2008/01/27(日) 23:15:08 ]
wchar_t(unsigned char) に入ったUTF16の日本語を
ShiftJISに変換してxharに突っ込む処理を
STLだけで書くにはどう書けばいいですか?

527 名前:デフォルトの名無しさん mailto:sage [2008/01/27(日) 23:26:27 ]
std::codecvt使う例が
hw001.gate01.com/eggplant/tcf/cpp/strcnv.hpp
にあるけど、UTF16、ShiftJISと指定した
std::codecvtをどう取得するのかは知らない

528 名前:デフォルトの名無しさん mailto:sage [2008/01/27(日) 23:48:39 ]
>>525
テンプレートは解決策の1つだとは思うけど、
ヘッダファイルに実装するのはどうもね・・・。
コードいじったときのコンパイル範囲が広くなると困るし。

529 名前:デフォルトの名無しさん mailto:sage [2008/01/28(月) 00:07:40 ]
OSに頼ったほうが安全

530 名前:デフォルトの名無しさん mailto:sage [2008/01/28(月) 00:09:31 ]
>>524
そのIAをIUnknown、Aを適当なインタフェースに置き換えれば、そんな例は山ほどある。

Aの実装をソースコードの形で手に入れられるなら、
普通にIBとAを多重継承して、細かいところを整えればいける。

531 名前:デフォルトの名無しさん mailto:sage [2008/01/28(月) 00:28:36 ]
>>530
むむっ。詳しくお願いします。

532 名前:デフォルトの名無しさん mailto:sage [2008/01/28(月) 01:31:57 ]
>>530
要は、本来Bでオーバーライドする必要のない関数も、B内から手動でAの実装を呼ぶようにすればいい。
インタフェースはメンバ変数ないから、キャスト関係くらいしか仮想継承の有無の違いはないといっても過言ではない。
struct IA : IUnknown {virtual HRESULT STDMETHODCALLTYPE FnA() = 0;};
struct A : IA {
    virtual HRESULT STDMETHODCALLTYPE QueryInterface(IID&, void**) {/*実装*/}
    virtual ULONG STDMETHODCALLTYPE AddRef() {/*実装*/}
    virtual ULONG STDMETHODCALLTYPE Release() {/*実装*/}
    virtual HRESULT STDMETHODCALLTYPE FnA() {/*実装*/}
};
struct IB : IA {virtual HRESULT STDMETHODCALLTYPE FnB() = 0;};
struct B : A, IB {
    virtual HRESULT STDMETHODCALLTYPE QueryInterface(IID&, void**);
    virtual ULONG STDMETHODCALLTYPE AddRef() {return A::AddRef();}
    virtual ULONG STDMETHODCALLTYPE Release() {return A::Release();}
    virtual HRESULT STDMETHODCALLTYPE FnA() {return A::FnA();} //オーバーライドしない気なら
    virtual HRESULT STDMETHODCALLTYPE FnB() {/*実装*/}
};
HRESULT STDMETHODCALLTYPE B::QueryInterface(IID& riid, void** ppv) {
    if (ppv == 0) {
        return E_POINTER;
    } else if (riid == IID_B)     {
        *ppv = static_cast<IB*>(this);
        AddRef(); //直接A::AddRef()でも可
        return S_OK;
    } else {
        return A::QueryInterface(riid, ppv);
    }
}
Javaのインタフェースの仕様だとBでのAddRef以下のようなことを書く必要がなかった気がする、ちょっとうらやましい。


533 名前:デフォルトの名無しさん mailto:sage [2008/01/28(月) 01:34:43 ]
委譲するわけですか。
うーん。委譲のコストが少し気になってしまいますね。
そんなもんなんでしょうか。

534 名前:デフォルトの名無しさん [2008/01/28(月) 13:31:23 ]
自分クラスに大小比較の演算子を定義して、<=を使おうと思ったら、
<と==の2つを定義するのではなく、<=を定義しないとだめだったのですが、
そういうものなのですか?


535 名前:デフォルトの名無しさん mailto:sage [2008/01/28(月) 13:33:46 ]
そういうものです。
そもそも、'<='が「小なりイコール」であると言う意味から再定義するわけですから。



536 名前:デフォルトの名無しさん mailto:sage [2008/01/28(月) 13:35:16 ]
>>534
つ[boost::operators]

537 名前:デフォルトの名無しさん mailto:sage [2008/01/28(月) 14:14:23 ]
>>534
以下は違う関数だからねえ
operator<()
operator=()
operator<=()
<=を使うということはoperator<=()をコールするわけで。

538 名前:デフォルトの名無しさん [2008/01/28(月) 16:23:28 ]
>>535-537
ありがとうございます。じゃあ自分クラスについては、なるべく「<=」は使わずに
<と==でなんとかするようにします。
boost::operatorsは、<と==をconst関数で定義して、publicでboost::operatorsを
継承すれば動きました。かなり便利そう。
ありがとうございました。

539 名前:デフォルトの名無しさん [2008/01/28(月) 18:45:01 ]
typedef struct { .... } hoge_struct;

#define TARGET_STRUCT hoge_struct
#define TARGET_STRUCT_STR ????????????

printf("type: %s\n", TARGET_STRUCT_STR );
printf("size: %d\n", sizeof(TARGET_STRUCT) );

表示
type: hoge_struct
size: 40

TARGET_STRUCTにあるhoge_struct部分は、任意の構造体名です。(色々変化します)
TARGET_STRUCT_STRが "hoge_struct" に(文字列)なるようにしたいのですが、
どんなマクロにすればいいのでしょうか?

540 名前:デフォルトの名無しさん mailto:sage [2008/01/28(月) 18:52:07 ]
言葉足らずでした。
型名であるTARGET_STRUCTを元に、文字列なTARGET_STRUCT_STRを作りたいという意味です。

541 名前:デフォルトの名無しさん mailto:sage [2008/01/28(月) 18:58:47 ]
# TARGET_STRUCT

542 名前:デフォルトの名無しさん mailto:sage [2008/01/28(月) 19:11:51 ]
>>541 ありがとうございました。

543 名前:デフォルトの名無しさん mailto:sage [2008/01/28(月) 19:28:58 ]
>>538
なんとかするとかじゃなくて「<」と「==」から「<=」を作ればいいじゃんか。
「<」と「==」が定義されてるならば「<=」は↓のようになる。
return A < B || A == B;
boost::operatorsは内部でそういうことをやってるだけ。


544 名前:デフォルトの名無しさん mailto:sage [2008/01/28(月) 21:53:36 ]
 よろしくお願いします。
 項書き換えを行うシステムを作るにあたって、今式の構造を木構造で表すことを考えています。
式は中値記法で書かれているので、基本的には一般的な構文木のように作ろうと思っています。
具体的には、ある内部ノードには演算子を格納し、その左と右の子供に項を格納するような2分木です。
 2項演算を表現するのにはこれで十分なのですが、 (X, Y, Z) のような三つ組みも表現しなければならないのです。
子供を3つ持つような木を作って、三つ組みを表現するときだけ3つ目の子供に項を格納すれば表現は可能になるのですが、
頻繁に三つ組みが現れるわけではないので、余分な子供はあまり持たせたくないと思っています。
 2分木で三つ組みを表現するうまい方法はないでしょうか。


545 名前:デフォルトの名無しさん mailto:sage [2008/01/28(月) 21:56:16 ]
演算子 A を考える場合に

   A1
   ∧
   X A2
    ∧
    Y Z

みたいにすればいいんじゃない?



546 名前:デフォルトの名無しさん mailto:sage [2008/01/28(月) 22:00:04 ]
単項演算子で無駄なノードが発生するのは別に構わんのん?

547 名前:デフォルトの名無しさん mailto:sage [2008/01/28(月) 22:01:13 ]
各ノードはふたつのポインタをもち、
それぞれは、
・自分の子供のひとつ(長男)
・自分のすぐ下の弟
を指すようにすれば2分木でいくらでも子供を持てる。
これは木構造を作るのに定番の方法なので覚えておくといいよ。

548 名前:デフォルトの名無しさん mailto:sage [2008/01/28(月) 22:44:46 ]
Visual Studio 2005なんですが、vector型の変数で名前をarrayにしたら、変数名が青くなってました。

intみたいに予約語なのかなとも思ったんだけど、特に問題なく動くんですが、青くなるのはなんでなんでしょう?

549 名前:デフォルトの名無しさん mailto:sage [2008/01/28(月) 22:50:10 ]
>>548
arrayはCLR配列の予約語だからじゃない?

550 名前:デフォルトの名無しさん mailto:sage [2008/01/28(月) 22:59:40 ]
>>549
即レスありがとうございます!
ほうほう、CLR配列で調べると確かに予約語っぽいですね。でも問題なしと考えてよいんでしょうか。

ついでにうかがいたいんですが、ちょい前までVC++6.0でつくっていたソースコードがあって、関数の引数にbool型をつかっていました。

そのソースを2005でダイアログベースで作っているプロジェクトで利用しようと思ったんですが、チェックボックスのValueがBOOL型になってまして、そのまま関数の引数にぶち込むと、次のように怒られました。

>warning C4800: 'BOOL' : ブール値を 'true' または 'false' に強制的に設定します (警告の処理)

これはどうすればよいんでしょう?

551 名前:デフォルトの名無しさん mailto:sage [2008/01/28(月) 23:02:56 ]
BOOL変数?true:false
とか。BOOLってintだからなー。
TRUE/FALSEの代わりに「エラー値」が入ってたりするし。

552 名前:デフォルトの名無しさん mailto:sage [2008/01/28(月) 23:09:57 ]
>>551
うわぁお!!

すげー、通りました、感動しています。

しかし6.0から2005にするといろいろ戸惑いますね。作業効率が半分くらいになった感じです。

553 名前:デフォルトの名無しさん [2008/01/28(月) 23:37:08 ]
>>545
 そうですね、こちらでも考えましたが、このような木の構造にするしかなさそうですね。

>>547
 アドバイス有り難うございます。
処理系を作るときに、こういう形で構文木を作るとネストされたリストも簡単に表現できるということで、
勉強したことがありました。確かに自分もよく使います。

 お二方、どうも有り難うございました。

554 名前:デフォルトの名無しさん mailto:sage [2008/01/29(火) 00:09:40 ]
>>552
6.0から2005だと色々変えないといけないところが出てくるだろうな。
new 失敗した時デフォで NULL 返すような古いコンパイラだからなあ。
まあ、変更が終われば大した違いはなくなると思うぜ。

555 名前:デフォルトの名無しさん [2008/01/29(火) 00:46:03 ]
LONG a=適当;
LONG b=適当;
LONG c=適当;

if(a*a + b*b > c*c) {
}

とした時に、
a*a等がLONGに収まる範囲を超えてしまったら、
どうなるのでしょうか?



556 名前:デフォルトの名無しさん mailto:sage [2008/01/29(火) 00:56:45 ]
>>555
LONGがlongのtypedefなら未定義

557 名前:デフォルトの名無しさん mailto:sage [2008/01/29(火) 01:22:40 ]
STLでウィンドウへ作ったり絵を描くクラスはどこにありますか?

558 名前:デフォルトの名無しさん mailto:sage [2008/01/29(火) 01:23:49 ]
ありません
gilを使ってください

559 名前:555 mailto:sage [2008/01/29(火) 01:32:29 ]
>>556
Win32APIを使ったプログラムで、
LONGは<windows.h>に定義されているモノです。たぶん。
未定義というのは、どうなるか分からないということですか。

560 名前:デフォルトの名無しさん mailto:sage [2008/01/29(火) 01:33:46 ]
世界ランク14位おめw
2chcity.myminicity.com/

ランク   国名      街             人口  (前日比)  前日
--- 1   US1      LUELand         326354 (+211)   326143
--- 2   US2      GoonTown        179482 (+711)   .178771
--- 3   Germany1  .isnichwahr.de       119091 (-654)   119745
--- 4   US3      CreateMyCity Forum  .87380  (+1982)   85398
--- 5   Poland1    #debian.pl         79594  (+1043)   .78551
--- 6   Germany2  upOTia             52443  (+399)    52044
--- 7   France1    Reze'Les Nantes     .41960  (+246)    41714
--- 8   Canada1   J-C Satanas & CO   .40995  (+721)    40274
--- 9   US4      retromundi        .40604  (+788)    39816
--- 10  France2    FanaZ           .39902  .(+1268)   38634
2↑ 11  Germany3   deluxebits         38770  .(+3199)   35571
1↓ 12  US5      .isnichwahr.at        .38234  (+78)    38143
1↓ 13  France3    gravure-news       .37204  .(+765)    36439
2↑ 14  Japan1     2ch_city          35637  .(+1970)   33667
1↓ 15  Spain1     Media-Vida         .35205  .(+686)    34519
1↓ 16  France4    Sguy            .35083  .(+1456)   33626
2↓ 17  Ireland1    .prapikilty          .35067  .(+871)    34196
--- 18  Spain2     benidaver         .34505  .(+914)    33591
--- 19  Germany4   directupload       ..32490  .(+82)    .32408
-↑ 20  Slovakia1    Legionar City       32056

561 名前:デフォルトの名無しさん mailto:sage [2008/01/29(火) 01:36:39 ]
>>559
そういうことです。

562 名前:デフォルトの名無しさん [2008/01/29(火) 05:15:49 ]
doubleとintの丸め誤差について質問しているものです。
SSE2命令で計算するとどうして3.55*100が355になるのか、どうしてもわかりません。
IEEEの仕様どおりの浮動小数点の計算方法だと、レジスタのサイズが52でも80でも128でも
doubleの3.55は実際には2.54999999...となってしまうと思うのですが、、、
gccでSSE2命令を有効にして作成したバイナリの逆アセンブルの結果をみると、
<元ソース>
int main(void) {
double d = 3.55;
int n = d * 100;
printf("%d", n);
}

<続く>

563 名前:デフォルトの名無しさん [2008/01/29(火) 05:17:36 ]
<続き>
<main関数の逆アセンブル結果>
80483c4: 8d 4c 24 04 lea 0x4(%esp),%ecx
80483c8: 83 e4 f0 and $0xfffffff0,%esp
80483cb: ff 71 fc pushl -0x4(%ecx)
80483ce: 55 push %ebp
80483cf: 89 e5 mov %esp,%ebp
80483d1: 51 push %ecx
80483d2: 83 ec 24 sub $0x24,%esp
80483d5: dd 05 d8 84 04 08 fldl 0x80484d8
80483db: dd 5d e8 fstpl -0x18(%ebp)
80483de: dd 45 e8 fldl -0x18(%ebp)
80483e1: dd 05 e0 84 04 08 fldl 0x80484e0
80483e7: de c9 fmulp %st,%st(1)
80483e9: dd 5d e0 fstpl -0x20(%ebp)
80483ec: f2 0f 2c 45 e0 cvttsd2si -0x20(%ebp),%eax
<以下はprintfを呼んでいるだけと思うので略>
をみてもなんでこうなるのか全然わかりません。
cvttsd2siの命令が、「64ビット倍精度実数を整数値に変換して汎用レジスタに
コピーします。」という内容らしいので、この動作がキモと思うのですが、これは
中でどういう動作をしてるのだろう。誰かご存知ありせんか?

長々とすいませんどうかよろしくお願いします。


564 名前:デフォルトの名無しさん mailto:sage [2008/01/29(火) 05:26:47 ]
When a conversion is inexact, a truncated (round toward zero) result is returned.
と書いてあるから3.54になるはずなのに変だねえ。

565 名前:デフォルトの名無しさん mailto:sage [2008/01/29(火) 08:06:51 ]
>>563
逆アスじゃなく、gccのアセンブリ出力を載せてくれ。0x080484d8なんてアドレス書かれてもなんだか判らん。



566 名前:デフォルトの名無しさん [2008/01/29(火) 09:06:52 ]
>>565
すいません。Cのコードは先のものと同じです。
main:
leal 4(%esp), %ecx
andl $-16, %esp
pushl -4(%ecx)
pushl %ebp
movl %esp, %ebp
pushl %ecx
subl $36, %esp
fldl .LC0
fstpl -24(%ebp)
fldl -24(%ebp)
fldl .LC1
fmulp %st, %st(1)
fstpl -32(%ebp)
cvttsd2si -32(%ebp), %eax
movl %eax, -12(%ebp)
movl -12(%ebp), %eax
movl %eax, 4(%esp)
movl $.LC2, (%esp)
call printf
<以下略>


567 名前:デフォルトの名無しさん mailto:sage [2008/01/29(火) 09:35:25 ]
だから、どうして.LC0とか.LC1の定義も省略するのかなぁ……

568 名前:デフォルトの名無しさん mailto:sage [2008/01/29(火) 10:46:51 ]
>>563
> cvttsd2siの命令が、「64ビット倍精度実数を整数値に変換して汎用レジスタに
> コピーします。」という内容らしいので、この動作がキモと思うのですが、これは
> 中でどういう動作をしてるのだろう。誰かご存知ありせんか?

ここまでくるとCPUアーキテクチャマニュアル見ないとわからん。
Intelのサイトにあると思うが、日本語であるかどうかわからん。


569 名前:デフォルトの名無しさん mailto:sage [2008/01/29(火) 11:03:35 ]
CVTTSD2SI--Convert with Truncation Scalar Double-Precision Floating-Point Value to Signed Doubleword Integer

F2 0F 2C /r  xmm/m64 切り捨てを使用して、xmm/m64の 1 つの倍精度浮動小数点値を r32 の 1 つの符号付きダブルワード整数に変換する。

説明
ソース・オペランド(第 2 オペランド)の 1 つの倍精度浮動小数点値を、デスティネーション・
オペランド(第 1 オペランド)の 1 つの符号付きダブルワード整数に変換する。ソース・オペ
ランドは、XMM レジスタまたは 64ビットのメモリ・ロケーションである。デスティネーショ
ン・オペランドは汎用レジスタである。ソース・オペランドが XMM レジスタの場合は、倍精
度浮動小数点値はレジスタの下位クワッドワードに置かれる。
変換が不正確な場合は、切り捨てられた(ゼロに丸められる)結果が返される。変換の結果が
符号付きダブルワード整数の最大値より大きくなる場合は、整数不定値(80000000H)が返さ
れる。

570 名前:デフォルトの名無しさん [2008/01/29(火) 12:08:40 ]
本当にありがとうございます。

自分もマニュアル見てみました。
結局動作としては、
1)3.55を80bitのレジスタ上で表現する。レジスタ上では3.55よりもわずかに小さい数として存在
2)fmulp命令を使って、1)の結果と100の積を計算する。
3)上の2)の結果をcvttsd2si命令を使ってint型に変換
になると。
>変換が不正確な場合は、切り捨てられた(ゼロに丸められる)結果が返される。
354.99999..からintへの変換はどう考えても「変換が不正確な場合は、」に該当すると思うのですが、
切り捨てると、354になると思うんですが、、、


571 名前:デフォルトの名無しさん [2008/01/29(火) 12:54:22 ]
何度もすいません。

-msse2付きでコンパイルしても、不正確になってしまうケースがありました。
int main(void) {
double d = 32.55;
int n = d * 100;
printf("%d\n", n);
return 0;
}
あとは、512.55, 513.55とか、8192.55, 8193.55とか。(これ以外にもかなり多い)
SSE2を使ったところで完全ではないようだし、なんだか不毛な感じもしてきた。
3.55については、たまたまSSE2で上手く計算できたケース、ということかな、と。


572 名前:デフォルトの名無しさん mailto:sage [2008/01/29(火) 13:05:19 ]
>>571
>567
手元の多桁演算処理に喰わせてみようと思うのだが……

573 名前:デフォルトの名無しさん mailto:sage [2008/01/29(火) 13:12:09 ]
私の所でOptimization(最適化)レベルを切り替えて実験してみた所
-O0で354、-O1で355になりました。
コンパイラはg++3.4.5です。

ソースコードをのぞいてみると、-O0は律儀に計算していましたが、
-O1の方はいきなり定数355をロードして終了していました。

574 名前:デフォルトの名無しさん mailto:sage [2008/01/29(火) 13:12:41 ]
.file "IEEE1.c"
.def ___main; .scl 2; .type 32; .endef
.section .rdata,"dr"
LC2:
.ascii "%d\12\0"
LC3:
.ascii "pause\0"
.text
.globl _main
.def _main; .scl 2; .type 32; .endef
_main:
pushl %ebp
movl %esp, %ebp
subl $8, %esp
andl $-16, %esp
movl $16, %eax
call __alloca
call ___main
movl $355, 4(%esp) ←これ
movl $LC2, (%esp)
call _printf
movl $LC3, (%esp)
call _system
movl $0, %eax
leave
ret
.def _system; .scl 2; .type 32; .endef
.def _printf; .scl 2; .type 32; .endef

575 名前:デフォルトの名無しさん [2008/01/29(火) 20:52:37 ]
std::vectorを使った場合で指定した添え字番号のオブジェクトを消す方法ってありますか?



576 名前:デフォルトの名無しさん mailto:sage [2008/01/29(火) 20:58:18 ]
vec.erase(vec.begin() + i);

577 名前:デフォルトの名無しさん mailto:sage [2008/01/29(火) 22:19:04 ]
C言語って1から覚えるとなると難しいでしょうか?

プログラム関係の職(未経験可)どうしてもやってみたくて
就こうと思ってるんだけど理系学校出てないから無謀かな…

スレ違いだったら凄くすいません…






[ 続きを読む ] / [ 携帯版 ]

前100 次100 最新50 [ このスレをブックマーク! 携帯に送る ] 2chのread.cgiへ
[+板 最近立ったスレ&熱いスレ一覧 : +板 最近立ったスレ/記者別一覧]( ´∀`)<252KB

read.cgi ver5.27 [feat.BBS2 +1.6] / e.0.2 (02/09/03) / eucaly.net products.
担当:undef