■過去ログ置き場に戻る■ 1- 前250 次250 最新50


[memo] "9999999999_00.html#R20" という感じで、URLの最後に "#RレスNo" を追加すると幸せになれます。

C++相談室 part12
501 名前:デフォルトの名無しさん :02/11/02 21:47
おお。
しかしまんまの結果やね。
多重継承のときは先頭から辿るんだろうか・・・

502 名前:デフォルトの名無しさん :02/11/03 00:18
こういう感じのクラス間で相互に定義が入れ子になるコードを書いているのですが
コンパイル時に先に読み込まれたほうであとから読み込まれるクラスが定義されて
なくてうまくコンパイルできません。何らかの形でクラス識別子を定義してやれば
いいんだとは思っているんですがVCのヘルプとか見渡してもどうしたらいいのか
よくわからないので質問させてもらいます。

【CMona.h】
#ifndef CMona_H
#define CMona_H
#include "CGiko.h"

class CMona{

public:
  CGiko* Giko;
}

#endif
---------
【CGiko.h】
#ifndef CGiko_H
#define CGiko_H
#include "CMona.h"

class CGiko{

public:
  void Copipe(CMona* Mona);
}

#endif

503 名前:デフォルトの名無しさん :02/11/03 00:23
それぞれに
class CMona;
class CGiko;
をつけくわえてみよう。

504 名前:デフォルトの名無しさん :02/11/03 00:37
Thanx! うまくいったよ(*^o^*)

505 名前:デフォルトの名無しさん :02/11/03 06:03
Berkeley DB みたいな感じのファイルDBで、商用でもフリーでかつオープンソースに
しなくてもいいラインセンスのライブラリってありませんか?

506 名前:デフォルトの名無しさん :02/11/03 06:24
>>505
Berkeley DB


507 名前:デフォルトの名無しさん :02/11/03 08:00
>>506
Berkeley DB はソース公開しない場合は有料だったと思ったが。

508 名前:デフォルトの名無しさん :02/11/03 08:55
んじゃcdb。
っていうかスレ違いだし。


509 名前:デフォルトの名無しさん :02/11/03 08:55
http://cr.yp.to/cdb.html>>508


510 名前:デフォルトの名無しさん :02/11/03 14:57
具象クラス10個を多重継承していいですか?
それとも、クラス設計から考え直すべきですか?

511 名前:デフォルトの名無しさん :02/11/03 14:58
>>510
コンポジションならそういう例もあるんじゃない?

512 名前:デフォルトの名無しさん :02/11/03 18:46
>510
is-a法則は成り立つ?
委譲じゃ解決できない?

>>511
理解できないので詳しい説明お願いします

513 名前:デフォルトの名無しさん :02/11/03 19:04
>>510
そんな風にたずねられたら、普通はヤメトケって言われるよ・・・

514 名前:デフォルトの名無しさん :02/11/03 20:22
template<class T,class S>struct STA{
typedef T(STA::*FUNC)(S);
FUNC func;
std::string name;
STA(){
name=typeid(T).name();
if("void"==name){cout<<"debug"<<endl;func=fff;}
(this->*func)();
}
void fff(void){cout<<"fff"<<endl;}
};
/**************************************************************/
void main(void)
{
STA<void,void> sta;
}
エラーじゃないんですが、何故かメモリリークします。どうやらstringが
原因らしいんですが・・・

515 名前:デフォルトの名無しさん :02/11/03 20:24
きもっ

516 名前:デフォルトの名無しさん :02/11/03 20:46
2次元配列を動的に作成するときに現在は
 float** array;
 array new float*[x];
 for (int i = 0; i < num; ++i){
  array[i] = new float[y];
 }
のようにしているんですが、一気に領域を確保することはできませんか?

517 名前:デフォルトの名無しさん :02/11/03 21:16
標準例外に関する質問です。
「引数の範囲が不正」な場合には
invalid_argument を投げるべきでしょうか?それとも
out_of_range を投げるべきでしょうか?
range_error という可能性も?

あと、ここらへんについて簡素かつ正確に書いてある書籍等はないでしょうか?

518 名前:デフォルトの名無しさん :02/11/03 21:18
glibcって何ですか?

519 名前:デフォルトの名無しさん :02/11/03 21:26
>>517
引数の範囲が数直線上の区間で表すようなものならば、out_of_rangeが
適切でしょう。そうでなくて、たとえばenumにないものを指定されたとか
NULLはダメなのにNULL突っ込んだとかはinvalid_argumentでしょう。

> あと、ここらへんについて簡素かつ正確に書いてある書籍等はないでしょうか?

それぞれの例外の説明を読むしかないのでは・・・

520 名前:デフォルトの名無しさん :02/11/03 21:26
>>516
float* array;
array = new float[x * y];

利用時は
array[x + (y * rangeX)];



521 名前:517 :02/11/03 21:30
>>519
レスありがとうございます。
out_of_range が(runtime_errorではなく) logic_error を継承しているのが
ちょっと解せなかったのですが、
そこらへんはあんまり気にしないほうが良いのでしょうか?

区間を表す場合に、「最小値」が「最大値」より大きい なんて場合には
どうすればいいのでしょうか?

522 名前:デフォルトの名無しさん :02/11/03 21:34
雑談レスだけど、例外の適切な使い分けがなかなかわからねーなー。

523 名前:デフォルトの名無しさん :02/11/03 21:37
適当にXXXExceptionクラスを作ってそれ投げてりゃ良いのよ。

524 名前:デフォルトの名無しさん :02/11/03 21:40
>>520
やはりそれしかないんですか。
それでは、それを使おうと思います。



525 名前:517 :02/11/03 22:11
>>522
ですよねー。Java や C# などの後発の言語に比べて中途半端というか、
所詮後付け感は否めないですよねー。

>>523
やってると混乱してきちゃうので…。
中途半端に標準ライブラリに含めないで欲しかったですね。
そうすれば思い切って独自仕様で固められたのに。

>>524
(実は >>520 は私だったのですが)
あと、インデックスに使う値を管理するクラスを作ると楽かも?
でもそれをするとテンプレートとか使って「配列クラス」を作りたくなってしまうという罠!みたいな。

526 名前:デフォルトの名無しさん :02/11/04 12:01
例外はクラスライブラリによって使い方が違ってくるから複数のクラスライブラリ使ってると
設計がかなり難しくなってくる。

Javaはライブラリもそろってるしメモリ食わなきゃそこそこいいんだが。

527 名前:デフォルトの名無しさん :02/11/04 17:15
Hoge* HogeCreater::creat() {
 return new Hoge();
}

Hogeクラスのインスタンスを返す↑って使い方あってる?
メソッドを抜けるとオブジェクトが勝手に破棄されるとか?

528 名前:デフォルトの名無しさん :02/11/04 17:36
>>527
されない。どこかでちゃんと解放してやれよ。

529 名前:デフォルトの名無しさん :02/11/04 19:13
>>527
あってる
恐れている間違いはこういう感じだろう。

return &Hoge(); // 関数を抜けたら不正になるオブジェクトへのポインタを返している!!

>>528
質問の意図を読み間違えていると思われ。

530 名前:デフォルトの名無しさん :02/11/04 19:24
>>529
多分お前がな。

531 名前:デフォルトの名無しさん :02/11/04 19:25
Hoge& HogeCreater::creat() {
 return Hoge();
}

何も考えずこうした方が良いと思うが

532 名前:デフォルトの名無しさん :02/11/04 19:27
>>531
だめぽ


533 名前:デフォルトの名無しさん :02/11/04 19:47
勉強をかねて、Visual C++ でMFCではなくAPI主体のアプリを作ってます。
可変長の文字列というのはどのように扱うのが一般的なのでしょうか?

1.GlobalAllocなどのAPIを使う
2.C++標準ライブラリのcstringを使う
3.(便利そうだから?)MFCのCStringを使う
4.その他

今のところは数十から多くて数百文字なのであらかじめ多めに見積もって
おいてもだいじょうぶだとは思ってますが、なんとなく気分的にいやなんです。

534 名前:デフォルトの名無しさん :02/11/04 19:48
>>514
bcc5.51, vc++6.0, gcc2.95.3-5どれもエラー

535 名前: ◆hMJAPH9PWA :02/11/04 19:48
>>531
自動変数のリファレンス反しちゃダメじゃん。
Effective C++の23項参照。

536 名前:デフォルトの名無しさん :02/11/04 19:49
>>533
>2.C++標準ライブラリのcstringを使う
stringでは?
(2)がベターだと思われ。勉強がてら(1)してみるのもおもしろいかも。


537 名前:デフォルトの名無しさん :02/11/04 19:50
(´-`).。oO(C++標準にcstringなんてあったっけ?)

538 名前:デフォルトの名無しさん :02/11/04 19:53
>>537
煽りはスピードが命。

539 名前:デフォルトの名無しさん :02/11/04 19:53
(´-`).。oO(string.hのC++版…可変長じゃねぇな)


540 名前:533 :02/11/04 20:00
レスありがとうございます
>>536
ありがとうございます 使ってみますです
>>537
stringでしたね 寝ぼけたこと言ってごめんなさいです
>>539
そうなんですか!? 少しパニくってきたけど
そのへんはがんばれば自己解決でけそうです

541 名前:デフォルトの名無しさん :02/11/04 20:03
可変長文字列はstrdup()で確保してfree()で解放するのが常識だろ
strdup()の返り値はチェックしなくてすむしな

542 名前:デフォルトの名無しさん :02/11/04 20:15
  ∧__∧
 (ミTдTミ) しくしくしくしくしくしくしくしくしくしくしくしく 

543 名前:デフォルトの名無しさん :02/11/04 22:13
C言語で書かれたWindowsのスケルトンプログラムをC++で書き直しているところなのですが、
コールバック関数をクラスの中に入れると、どうしてもエラーが出てしまいます。

DirectXのサンプルプログラムを見てみると

基底のクラスで
class CD3DApplication
{
protected:
                :
  
static INT_PTR CALLBACK SelectDeviceProc( HWND hDlg, UINT msg,
WPARAM wParam, LPARAM lParam );

となっていました。そこで「SelectDeviceProc」をmsdnの検索キーワードにかけたのですが該当する
関数は見つかりませんでした。

誰か教えてください。

544 名前:デフォルトの名無しさん :02/11/04 22:19
ちなみにエラーの内容は、

error C2440; '='; 'LRESULT(_thiscall test_app::*)(HWND, UINT, WPARAM, LPARAM)'から'WADPROC'に変換できません。

wc.hIconSm=NULL;
wc.cbClsExtra=0;
wc.cbWndExtra=0;
wc.lpfnWndProc=WndProc;<-----ここ

if( !RegisterClassEx(&wc) )

545 名前:デフォルトの名無しさん :02/11/04 22:19
>>543
C++のメソッドは

A::hoge() -> hoge(A *this)

な感じになっています。

546 名前:デフォルトの名無しさん :02/11/04 22:21
画像が貼れるチャットがあるよ
http://www.i-chubu.ne.jp/~tomomi-h/marion/navi/navi.cgi?links=20311

547 名前:デフォルトの名無しさん :02/11/04 22:22
>>545 thanks

535はだだ今勉強中

548 名前:デフォルトの名無しさん :02/11/04 22:25
ちゃんとstaticつけたか?

549 名前:デフォルトの名無しさん :02/11/05 00:25
int *p(0);
がこけるんだけど、C++の仕様?それともVC6の制限?
ポインタはexplicitな宣言できないのかな?
でも、
int (*pf)(void)(0);
は通るんだなあ・・・

550 名前:デフォルトの名無しさん :02/11/05 00:27
こけるって?

551 名前:デフォルトの名無しさん :02/11/05 00:28
>>549
>int *p(0);
コンパイル通りませんけど。

552 名前:デフォルトの名無しさん :02/11/05 00:28
typedef int* INTP;
INTP p(0)
は?

553 名前:デフォルトの名無しさん :02/11/05 00:38
CとC++のどちらからでも勉強できるのですか?

554 名前:デフォルトの名無しさん :02/11/05 00:39
>>549
それ、コンパイラには int *(p(0)); と解釈されてると思うんだがどうよ?
演算子の優先順位的に。

555 名前:デフォルトの名無しさん :02/11/05 00:40
>>553
ええ、そうですよ。

556 名前:デフォルトの名無しさん :02/11/05 00:42
>>555
まったくの初心者なんですが、プログラミング言語を勉強する前に何か本などを読んで方がいいのでしょうか?

557 名前:デフォルトの名無しさん :02/11/05 00:45
まったくの初心者なら、スクリプト言語辺りを軽く触っておいてから
挑むのが良いかもれ知れませんね。

558 名前:549 :02/11/05 00:53
レスさんくす。
規格読んでたんだけど、それらしき記述は見つけられず。残念。
>>552
確かに、typedefしたら通りました。
>>554
なるほど。エラーメッセージが一緒だな。どうもそれみたい。
まあ、素直にふつうに宣言するのが無難だな。

559 名前:デフォルトの名無しさん :02/11/05 01:01
typedefしても通らんぞ(gcc3.2)。
VC++がおかしいんじゃないの?

560 名前:549 :02/11/05 01:05
>>559
VC6では確かに通ったよ。
それはそうと、宣言じゃなく初期化だな。恥ずかしい・・・

561 名前:デフォルトの名無しさん :02/11/05 01:07
>>560
ああ了解。拡張子を.cにしていました。スマソ。
そうか、int (*p)(0); は、int *p = 0; と同じなのね。

562 名前:デフォルトの名無しさん :02/11/05 10:00
>>543
プロシージャにしたいメンバ関数を
static LRESULT CALLBACK WindowProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam);
としてwc.lpfnWndProc = WindowProc;で何も問題無い

ちなみにstaticな関数なので、プロシージャの中からメンバにアクセスしたい場合は
プロシージャの最初のほうでWM_CREATEのlParamからlpCreateParamを拾って保持しておく必要がある

static 自作ウィンドウクラス* Instance = NULL;
if (Instance == NULL) {
 if(msg == WM_CREATE) {
  Instance = static_cast<自作ウィンドウクラス*>(reinterpret_cast<LPCREATESTRUCT>(lParam)->lpCreateParams);
 }
 return DefWindowProc(hWnd, msg, wParam, lParam);
}

アクセスする場合はInsctance->メンバ

563 名前:デフォルトの名無しさん :02/11/05 20:27
仮想関数デストラクタについて質問。

C++ FAQ等を見ていると
class CA{
public:
CA();
virtual ~CA();
};
のように、
デストラクタが、仮想関数になってるのですが、
virtual にしても、しなくても変化が無いように見えますが
仮想関数にする意味があるんでしょうか?



564 名前:デフォルトの名無しさん :02/11/05 20:30
>>563
C++ FAQ見れ

565 名前:デフォルトの名無しさん :02/11/05 20:35
継承しないなら、関係ない。

566 名前:563 :02/11/05 20:40
>>564
それについて、
コンストラクタとちがって
virtualキーワードをつけて宣言できる。
としか書いてないのです。

つけても、つけなくても、
継承元デストラクタ→継承先デストラクタ
が呼ばれるのです。
オーバーライドしようと、継承先で~CA()と書いてもエラー出るし。
よくわからないので、おしえてください。


567 名前:デフォルトの名無しさん :02/11/05 20:52
>>566
例えばclass CAから派生したclass CBがあったとして、そのポインタを
親のCAで表現しているとき

CA* cap = new CB;
delete cap;

とした時、~CA()も~CB()も仮想デストラクタにしておかないと、~CB()が
呼び出される保証はない。

568 名前:566 :02/11/05 21:02
>>567
うおお。
わかりました。
わかりすぎて、少し感動しました。
ありがとうございますー。

569 名前:デフォルトの名無しさん :02/11/05 21:03
これが意図した動作かどうか確かめてみそ。

class CA {
public:
~CA() { std::cout << "~CA()\n"; }
};

class CB : public CA {
~CB() { std::cout << "~CB()\n"; }
};

int main()
{
CA* cap = new CB;
delete cap;
}

570 名前:デフォルトの名無しさん :02/11/05 21:38
class CA {
public:
vittual ~CA() { std::cout << "~CA()\n"; }
};

class CB : public CA {
~CB() { std::cout << "~CB()\n"; }
};

int main()
{
CA* cap = new CB;
delete cap;
return 0;
}

は OK? NG?

571 名前:デフォルトの名無しさん :02/11/05 21:49
>>570
OKですよ。基底クラスのデストラクタが仮想デストラクタになると、
それ以降継承されたクラスのデストラクタはデフォルトで(というか
強制的に)仮想デストラクタになるから。

572 名前:デフォルトの名無しさん :02/11/05 21:52
お、vittualはvirtualですよね。念のため。

573 名前:デフォルトの名無しさん :02/11/05 21:58
Effective-C++のP78〜84には、基底クラスのデストラクタを仮想デスト
ラクタにするべき時とそうでない時についての考察が書かれている。

大まかに言えば、継承するつもりのないクラスのデストラクタは仮想に
すべきでなく、継承するつもりならば仮想デストラクタにしておけば安心
であるというような内容。

574 名前:570 :02/11/05 21:59
#define vittual virtual
逝ってくる・・・

571 アリガ`

575 名前:デフォルトの名無しさん :02/11/05 21:59
クラスに少なくとも1個の仮想関数が含まれていれば、仮想デストラクタ
を宣言すること、となっている。

576 名前:デフォルトの名無しさん :02/11/05 22:05
なんでコンパイルできないの?

class CA {
public:
virtual ~CA() = 0;
};

class CB : public CA {
public:
~CB() { std::cout << "~CB()\n"; }
};

class CC : public CB {
public:
~CC() { std::cout << "~CC()\n"; }
};

int main()
{
CA* cap = new CC;
delete cap;
}

577 名前:デフォルトの名無しさん :02/11/05 22:10
>>576
純粋仮想関数であってもデストラクタの場合は実体が必要。
だから

CA::~CA() {}

などの定義を行えばよい。

578 名前:デフォルトの名無しさん :02/11/05 22:12
>>577
即レスありがとうございますぅ。でもどうしてデストラクタの場合だけ
実体がないとエラーになるのでしょうか?C++3rdのどの当たりにその
ような事が書いてあるかわかりますか?

579 名前:デフォルトの名無しさん :02/11/05 22:13
腐ってんね。

580 名前:デフォルトの名無しさん :02/11/05 22:20
>>578
Effective-C++のP83にそのような事が書いてある。

デストラクタは純粋仮想関数の中でも特別な扱いで、基底クラスのデストラクタ
の呼び出しをコンパイルしてしまうため、リンク時にエラーになるとある。

他の純粋仮想関数ではこうはならない。

581 名前:デフォルトの名無しさん :02/11/05 22:25
>>580
どうもありがとうございます。もう少しデストラクタについて勉強
してみます。

582 名前:デフォルトの名無しさん :02/11/05 22:27
class hoge {
public:
 virtual void huga() = 0;
};
void hoge::huga()
{
 cout << "huga" << endl;
}

583 名前:デフォルトの名無しさん :02/11/05 22:31
>>582
その場合huga()はどうやって呼び出すの?

584 名前:デフォルトの名無しさん :02/11/05 22:36
class hage: public hoge {
public:
 void huga() {}
 void age() { hoge::huga(); }
};
int main()
{
 hage sage;
 sage.age();
 return 0;
}

585 名前:デフォルトの名無しさん :02/11/05 22:39
>>584
なるほど・・・・こうなると、純粋仮想関数も糞もあったもんじゃないですね。
直接呼び出せなくなっているだけで間接的には呼び出せるのか。

586 名前:デフォルトの名無しさん :02/11/06 00:06
>>561
g++3.0でこんな実験をやってみた。
typedef int *intp;
const int *x(0);
としておくと、
int *y(0), int (*y)(0), int *(y(0)), int (*y(0)), intp y(0)
は全部同じエラー(const外し)になって、
intp y = intp(x);
は通った。intp(x)はCスタイルの(intp)xと同じになるみたい。
参考までに。

587 名前:デフォルトの名無しさん :02/11/06 00:14
int main()
{
 int i(); //default constructor?
 i = 0; //oh error!
 return 0;
}

588 名前:デフォルトの名無しさん :02/11/06 00:18
>>586
> const int *x(0);
え?

589 名前:588 :02/11/06 00:32
> const int *x(0);

これ何でコンパイル通るの?
* 演算子より () 演算子の方が優先順位高いはずだけど・・・。

590 名前:543 :02/11/06 00:36
>>562さん 

詳しい説明ありがとうございました。

そのおかげで何とかできました。

今は、自作関数をC++に書き直してているのですがまた分からない事があったらよろしくお願いします。

591 名前:デフォルトの名無しさん :02/11/06 00:38
const int * x = 0;

592 名前:588 :02/11/06 00:46
>>591
いや、const int (*x)(0); ならそうなるのもわかるんだけど。
const int *x(0); なのにそうなるのなら理由がわからない。

593 名前:587 :02/11/06 00:47
>>589
xは0で初期化され、その型はconst int *である、と読めると思うが?
それよりint (*x)(0);が通るのが不思議。*xが0で初期化される、と
読まれて、エラーになりそうなものだが、int *x = 0;と同じように
解釈されている。まあint *x = 0;だって、普通の優先順位で考えたら
*xが0になりそうなものだが。・・・今試してみたら、
int (*x) = 0;
が通ったよ。

594 名前:デフォルトの名無しさん :02/11/06 00:49
>>589
変数宣言の所の * とか [] とか () とかは演算子ではないと思うが。
コンストラクタ呼び出しの()はともかく。

595 名前:588 :02/11/06 01:01
>>593
int (*func)(int arg); って例があるもんだから。
・・・あれ? 余計混乱してきたような・・・。
>>594
うーん、「そういうものだ」 と思い込むしかないのか・・・。

596 名前:age :02/11/06 03:31
vc6.0のデバッグで関数に飛ぶと 
シンボル this
値    error変数にスタックフレームが必要です
という のが表示されてしまっています。

これはどのような時に表示されるのでしょうか?
特に実行がおかしいわけではないのですが気になってしょうが
ありません。

597 名前:デフォルトの名無しさん :02/11/06 03:47
>>596
標準スタックフレームの生成を外しているとか。

598 名前:デフォルトの名無しさん :02/11/06 03:55
大抵の関数には、突入時に、自動変数領域の確保や
引数の取り出し用に、ebp,espを操作します。
スタック操作が完了していない場合、
「変数にはスタックフレームが必要」が出てくると思われます。

class A{ public:int Val;
void setA(int v)
{Val = v; }
void setB(int v)
{
Val = v;
}};
int main()
{A a;
a.setA(2);
a.setB(55);
}
ウオッチウインドウにthisを追加して、上のコードをステップ実行すれば、
大体わかるとおもいます。混合モードをステップ実行するのも良いでしょう。

599 名前:デフォルトの名無しさん :02/11/06 14:39
Visual Fortranで作成したプログラムをVC++上で走らせるにはどうしたらいいですか?
一応C++に移植したのですが変な動作するので、あきらめてフォートランの方のを
使おうと考えているのですが。

600 名前:デフォルトの名無しさん :02/11/06 14:47
>>599
答えられる奴は神


601 名前:デフォルトの名無しさん :02/11/06 14:48
>>599
DLLにするのが賢い気がする。

602 名前:デフォルトの名無しさん :02/11/06 14:53
>>599
そりゃ、忠実に移植するしかないだろ。

603 名前:デフォルトの名無しさん :02/11/06 15:22
こんにちは。質問させてください。

C言語で
struct main_data{
double z
}data;
(struct main_data*)malloc(sizeof(struct main_data)*810000)
というふうに構造体を作りメモリを確保し、

for(int i=0; i<900; i++){
for(int j=0; j<900; j++){
(data+j+i*900)->z = nodata;
}}

としたものがあります。

それをC++で
struct main_data{
double z[810000];
}data;
とし、newでメモリを確保したなら、
↑のfor文を書くならどうすればよいでしょうか?

どなたかよろしくお願いします。


604 名前:デフォルトの名無しさん :02/11/06 15:24
>>603
C++でもmalloc使える。

605 名前:デフォルトの名無しさん :02/11/06 15:35
てゆーかさ、メモリブロックをまとめて「配列として」確保したんだから、Cでも
for(int i=0; i<900; i++){
for(int j=0; j<900; j++){
data[j+i*900].z = nodata;
}}
とするのが普通だと思うんだが。

606 名前:デフォルトの名無しさん :02/11/06 15:38
fill(&z[0], &z[810000], nodata);

607 名前:603 :02/11/06 15:38
>>604、605
レスありがとうございます。

すいません、書き漏れ。
C++で、
struct main_data *data0;
data0 = &data
としています。
自分は
data0->z[j+i*900] = nodata;
だと思うのですが、いかかでしょうか?

608 名前:デフォルトの名無しさん :02/11/06 15:41
aha?

609 名前:デフォルトの名無しさん :02/11/06 15:42
クラステンプレート内で仮想関数を宣言することに意味は見出せますか?


610 名前:デフォルトの名無しさん :02/11/06 15:42
あは♪

611 名前:デフォルトの名無しさん :02/11/06 15:42
>>609
割と。

612 名前:デフォルトの名無しさん :02/11/06 15:46
>>611
具体例キボンヌ


613 名前:デフォルトの名無しさん :02/11/06 15:57
> struct main_data{
> double z[810000];
> }data;

普通に

struct main_data{
double z[900][900];
}data;
じゃいかんのか?

614 名前:デフォルトの名無しさん :02/11/06 15:58
       /■ヽ
      (´Д`)
  (( ─━OO━─ ))
        ∪∪

615 名前:603 :02/11/06 16:01
>613
多分いいと思いますが、いまさら書き直す気力がありません。。。

616 名前:デフォルトの名無しさん :02/11/06 20:12
>>612
ATL の CWindowImplBaseT とか。

617 名前:デフォルトの名無しさん :02/11/06 20:58
>>602
C から FORTRAN 側の関数を呼べるんじゃないかなぁ。VC++ は知らんが、
その昔 UNIX でやった覚えがある。

618 名前:デフォルトの名無しさん :02/11/06 22:09
class explicit_class
{
public:
virtual explicit_class(){};//error
virtual ~explicit_class(){};
virtual explicit_class(const explicit_class&){};//error
virtual explicit_class& operator=(const explicit_class&) = 0;
virtual explicit_class* operator&() = 0;
virtual const explicit_class* operator&() const = 0;
};

コンパイルできないんだけど、やっぱり無理なんでしょうか?

619 名前:デフォルトの名無しさん :02/11/06 22:13
コンストラクタにvirtual宣言?

620 名前:デフォルトの名無しさん :02/11/06 23:05
>>619
サンクス
コンストラクタにはvirtual宣言できないのね。
コンストラクタの記述の強制はできないのか...。
//修正
class explicit_class
{
public:
explicit_class(){};
explicit_class(const explicit_class&){};
...後は同じ
};

class A :public explicit_class
{
public:
A(){}
A(const A& i){*this = i;}
~A(){}
A& operator=(const explicit_class& i){return *this;}//両方必要
A& operator=(const A& i){return *this;}//両方必要
A* operator&(){return this;}
const A* operator&() const{return this;}
};

int main()
{
A a,b;
a=b;
}

621 名前:デフォルトの名無しさん :02/11/07 02:02
>>599
Fortranしらないんで、適当だけど
#define IF if(
#define THEN ){
#define ENDIF }
とかする。

622 名前:デフォルトの名無しさん :02/11/07 02:07
>>621
そういう事は絶対にやめれ。

623 名前:デフォルトの名無しさん :02/11/07 07:54
timeGetTime() ってどのくらいはかれるんでしょうか?一時間とかいけます?

624 名前:デフォルトの名無しさん :02/11/07 08:31
>>623
WIN32API行き

625 名前:デフォルトの名無しさん :02/11/07 11:37
vector について(?)です

class CTEST
{
  LPSTR  m_var ;
public:
  CTEST::CTEST() { m_var = new CHAR[10]; } ;
  CTEST::~CTEST() { delete [] m_var; } ;
  void operator = ( LPSTR lps ) { strcpy(m_var, lps); } ;
};

// 処理
...
 vector<CTEST>  vecTest ;
 CTEST      cTmp ;

 for ( long i=0; i < 10; i++ )
 {
   cTmp = "(・∀・)" ;
   vecTest.push_back( cTmp ) ;
 }

とすると、3回目の push_back で例外がボーン・・・
(→ HEAP[FORDEBUG.exe]: Invalid Address specified to RtlValidateHeap( 00370000, 00370FE0 )

ただし、メンバを LONG にしたり CHAR m_var[10] とかの場合は問題なしです。
動的に確保したものはダメなんでしょーか?


626 名前:デフォルトの名無しさん :02/11/07 11:45
>>625
void operator = ( const CTEST& ) { ... } ;

こっちの代入演算子を定義してないからじゃないかな?


627 名前:デフォルトの名無しさん :02/11/07 11:50
なぜ代入演算子の戻り値が void なんだ?
コピーコンストラクタもないし突っ込みどころ満載だな。
例外の原因は new CHAR[11] かな。

628 名前:625 :02/11/07 13:54
>>626 >>627
ありがd。
解決しますた。

1. コピーコンストラクタが無いからデフォルトコピーコンストラクタが呼ばれる
2. メンバをそのままコピー
3. デストラクタであぼーん
ということですか。。。

下を追加したら動きました。

  CTEST::CTEST( const CTEST& cc)
  {
    m_var = new char[10];
    strcpy(m_var, cc.m_var) ;
  } ;
  CTEST &operator = ( const CTEST& cc)
  {
    if (this != &cc)
    {
      m_var = new char[10];
      strcpy(m_var, cc.m_var);
    }
    return *this;
  } ;


629 名前:デフォルトの名無しさん :02/11/07 14:33
"(・∀・)" は char[10] に収まるの?

630 名前:デフォルトの名無しさん :02/11/07 14:57
>>629
Shift-JIS で 8 バイトですが何か?

631 名前:625 :02/11/07 15:05
>>629
ぎりぎり入るけど
strcpy なのでアウトでしたね。
ていうか 初期化もしてなかったし・・・
回線切って首つってきます。

632 名前:デフォルトの名無しさん :02/11/07 18:11
STL使っているなら素直にstring使えば。

633 名前:デフォルトの名無しさん :02/11/08 07:47
class T { class N{}; };

↑で定義される T::N を、
class T; みたいに名前の宣言だけってできますか?
class T::N; だとエラーになります。

634 名前:デフォルトの名無しさん :02/11/08 08:43
>>633
>できますか?
試しなさいよ。

構造体と事情は一緒ではなかったかい?

635 名前:633 :02/11/08 08:57
> 試しなさいよ。
> 構造体と事情は一緒ではなかったかい?

事情が同じなら class T::N; で試した段階で
宣言できて欲しいところですが。
エラーになるデスヨ。

636 名前:デフォルトの名無しさん :02/11/08 11:28
>>635
T クラスが事前に定義されていないと T::N のように限定することはできなかったと思う。



637 名前:その1 :02/11/08 12:08
class Class_Test079{
public:
class Class_Test080;
class Class_Test081;
class Class_Test080{
public:
Class_Test081* m_pointer;
Class_Test081* Func(){cout<<"\nClass_Test080::Func"<<endl;return m_pointer;}
}hoge;

class Class_Test081{
public:
Class_Test080* m_pointer;
Class_Test080* Func(){cout<<"\nClass_Test081::Func"<<endl;return m_pointer;}
}hage;
};

638 名前:その2 :02/11/08 12:09
int
main(){//確認用
class Class_Test079 a;
a.hoge.m_pointer = &a.hage;
a.hage.m_pointer = &a.hoge;
a.hoge.m_pointer->Func()->Func()->Func()->Func()->Func()->Func()->Func()->Func()->Func()->Func()
return 0;
}

639 名前:その2' :02/11/08 12:11
おっとmainのFunc()にセミコロンが抜けた。

こういうことがやりたかったのか?

640 名前:デフォルトの名無しさん :02/11/08 14:57
私の悩み、聞いてくれます?
C覚えて、その後Java覚えて、再びCのプログラム書こうと
してるけどJavaの悪い癖(参照)がついてしまって、なかなか
ポインタが使えません・・・
リスト構造関連の優秀なWebページを教えていただけませんか?
あ、「猫でも分かる・・・」は勘弁してください。デムパ嫌いですから。

641 名前:デフォルトの名無しさん :02/11/08 15:48
>>629
6バイトでいけるんちゃうか?


642 名前:デフォルトの名無しさん :02/11/08 17:08
>>640
> 私の悩み、聞いてくれます?
> デムパ嫌いですから。

そうですか。それは大変ですね。

643 名前:デフォルトの名無しさん :02/11/08 21:56
>>640
ここはC++相談室ですが?

644 名前:633 :02/11/08 23:44
>>639
うーん、class T が定義されてるヘッダをインクルードせずに、
T::N の名前を使いたい・・・。
こうして書いてみると、できなくてあたりまえのような気がしてきたり。

645 名前:デフォルトの名無しさん :02/11/09 00:25
メンバに含めるって事はサイズがわからなきゃダメだから
宣言だけでは無理だよ

646 名前:639 :02/11/09 01:38
というかnamespaceの問題だと思う。
T::ときたらTの名前空間はコンパイラが知っていなければ
ならない。

647 名前:名無しさん@Emacs :02/11/09 04:39
継承とポインタをからめたんだけど:

class Base {
 int a;
};

class Derived : public Base {
 int b;
};

void
aho(Derived *p)
{
 Base *p1 = p;
 Base b;
 *p1 = b;
}

で、 *p に Base の instanceが入っちゃうじゃん!!
っていうのは問題じゃないの?
型安全性が... とか考えちゃうんだけど。



648 名前:デフォルトの名無しさん :02/11/09 05:25
>>647
class Base
{
public:
  Base() { a = 1; }
  virtual void print() { cout << "Base: " << a << endl; }
protected:
  int a;
};

class Derived: public Base
{
public:
  Derived() { a = 3; b = 5; }
  void print() { cout << "Derived: " << a << ", " << b << endl; }
private:
  int b;
};

void aho(Derived *p)
{
  Base *p1 = p; cout << "p1->print(): "; p1->print();
  Base b; cout << "b.print(): "; b.print();
  *p1 = b; cout << "p1->print(): "; p1->print();
}

Base 分のメンバだけはコピーされる。
Derived 分のメンバはそのまま。
それが問題というなら問題だけど、そうでないならどうでもいいと思う。

649 名前:デフォルトの名無しさん :02/11/09 05:58
Baseの代入演算子をprivateあるいはprotectedにしとけば
一応回避はできるね。

その手の本を読むと、「コピーコンストラクタと代入演算子は
定義するか、あるいはprivateにせよ」と書いてある。

650 名前:デフォルトの名無しさん :02/11/09 06:36
typedef使えばいいんじゃん。
#include<iostream>

struct a{
struct b{
b(){ std::cout << "test"; }
};
};
typedef a::b b;

void f(){
class c{};//関数内のクラスはfinalです
}

int main()
{
a A;
b B;
//c C;//これはコンパイルできない
}

651 名前:デフォルトの名無しさん :02/11/09 06:49
>633
T::Nを必要とする部分をテンプレートにしてまえば、
前方宣言要らへんのとちゃう?

652 名前:デフォルトの名無しさん :02/11/09 09:27
>>647
もちろん問題だが、もしそれを解決しようと思ったら常に

 そのポインタが指してるデータの型は、本当は何?

っつーのをチェックする必要がある。これはコストが大きいから、C++ では
敢えて危険な方をデフォルトにしてる。

C++ だと継承を使っているオブジェクトに関しては、値のコピーはふつー
認めないように operator=() を private にしておく。ポインタのコピー、ある
いは参照を常に使い、操作はメンバ関数 (往々にして virtual) で。

653 名前:デフォルトの名無しさん :02/11/09 10:30
> そのポインタが指してるデータの型は、本当は何?

これを言語レベルでやるなら、VB の Variant 型を実装する事になるな。
void* ポインタに対して任意のメソッドが使えたりして。

654 名前:名無しさん@Emacs :02/11/09 12:31
>>648 それは確認したんで、主張としては弱いかと思ったんだけど。
>>649,652 やぱーり知られた問題で解決法があったんだねえ。
たしかに copyを制限して、フツーの OOPLみたいにするのがいいんだろうね。

あと、 int (*)(const T&) と int (*)(T&) の間のキャストとか
vector<const T> と vector<T> の関係とか気になったのだけど、
ここらもおしてしるべしかしらん。

void* を int* に変換できなかったり、多重継承したクラスのポインタを
親クラスのポインタにすると値が変わっちゃうぐらい気を使ってるんだから
そこらへんもなんとかなってほしかった C & Haskell使いでした。


655 名前:デフォルトの名無しさん :02/11/09 13:10
>>654
関数ポインタは、いずれもキャスト可能。しかも C 時代の遺物だから
実行時型情報は使えないので危ないことこの上ない。C++ 的には、
関数オブジェクトを使うのがお奨めかと。

> そこらへんもなんとかなってほしかった
まぁ、過去との互換性の問題とか何とか、いろいろしがらみ多い言語
だから。

コピー禁止に関しては boost を入れて boost::noncopyable を継承する
のが楽。#inculde と合わせても 2 行で済むし。

656 名前:デフォルトの名無しさん :02/11/09 20:27
メンバー変数を配列にすることはできないんでしょうか?


657 名前:デフォルトの名無しさん :02/11/09 21:27
class Hoge
{
 int hogehoge[100000];
};
ならできるけど、そういう話じゃなくて?

658 名前:デフォルトの名無しさん :02/11/09 21:47
>>657
すいません、説明不足でした。

hairetu[10000]={ m_member1 , m_member2 , ................. }

みたいなことをやりたいんです。
メンバ変数を連番にしているのでfor文とかで使いたいと
思ったのですが。。

659 名前:デフォルトの名無しさん :02/11/09 21:53
>>658
657 にすればいい話じゃなくて?
どうしても名前付き変数名とインデックスを使い分けたいなら、union にでもすれば。

660 名前:659 :02/11/09 21:54
「名前付き変数名」 って何かおかしいけどナー。

661 名前:デフォルトの名無しさん :02/11/10 00:11
>>658

(・∀・)?

662 名前:デフォルトの名無しさん :02/11/10 00:20
>メンバ変数を連番にしているのでfor文とかで使いたい
配列の立場は・・・?

663 名前:デフォルトの名無しさん :02/11/10 00:22
>>658
なにしたいんだかよくわからん

struct hoge {
int arr[100] ;
} ;
ならば
hoge h={1,2,3,4} ;
または
hoge i={{1,2,3,4}} ;

それとも
struct hoge {
int a1 ;
int a2 ;
int a3 ;
} ;

int hoge::*p[3]={&hoge::a1,&hoge::a2,&hoge::a3} ;

とか

664 名前:デフォルトの名無しさん :02/11/10 00:23
>>658
enumで定数を定義して定数と要素数に対応した
処理で決着というオチが見えるのだが。

665 名前:デフォルトの名無しさん :02/11/10 00:34
class Hoge {
 int m_member1;
 int m_member2;
 ...
 int m_member10000;
}

という 「定義済みの」 class があって、そのメンバを 「外部から」 配列で
使いたいという話か? なら、

   設 計 か ら や り 直 し て く れ 。

どうしてもと言うなら
int *hairetu[10000] = { &m_member1, &m_member2, ... &m_member10000 };
for(int i = 0; i < 10000; i++)
 DoSomething(*hairetu[i]);

でも繰り返すが、

   設 計 か ら や り 直 し て く れ 。

そもそも連番のメンバ名なんか使うな。
くれぐれも、設計からやり直してくれ。

COBOLer のにほいがぷんぷんと・・・

666 名前:デフォルトの名無しさん :02/11/10 00:57
>>657-665
大人なんだから望みをかなえてやれヨ!

#include "boost/preprocessor/repetition/repeat.hpp"
#include "boost/preprocessor/punctuation/comma_if.hpp"
#define MEMBER_MAX 10000
#define MACRO(z,n,d) BOOST_PP_COMMA_IF(n) d##n
class A {
public:
int BOOST_PP_REPEAT(MEMBER_MAX, MACRO, m_member);
};
int main() {
A a;
int hairetu[MEMBER_MAX] = {BOOST_PP_REPEAT(MEMBER_MAX, MACRO, a.m_member)};
return 0;
}


667 名前:デフォルトの名無しさん :02/11/10 01:20
>>666
658 の望みは叶えられない方が周りが幸せなんだが。
つーか、class 定義いじれるなら union でいいだろ。

668 名前:デフォルトの名無しさん :02/11/10 02:57
JDK1.4を入れてたんだけど
さっきインターネットしてたら、1.2がインストールされて、デフォルトが1.2になっちまったよ。。
どうすれば1.4に戻るの?コントロールパネルのJava-Plug Inをどうにかするの?

669 名前:デフォルトの名無しさん :02/11/10 02:58
>>668
ここはC++スレッド

670 名前:デフォルトの名無しさん :02/11/10 06:55
ID「C++」でますた…

671 名前:デフォルトの名無しさん :02/11/10 07:49
>>670
どこ

672 名前:デフォルトの名無しさん :02/11/10 09:43
クラスを作成してその中で配列を使うとき、

class A{

public;
char a[70][2];
................
}
として
コンストラクタで初期化するときに

a[70][2]={"aa","bb",......}

というように一度に初期化はできないんでしょうか?

673 名前:デフォルトの名無しさん :02/11/10 10:14
>>672
言ってる意味分からん。
どうでもいいが、文字2つを文字列として扱うなら、 a[70][3] じゃねーの?

674 名前:デフォルトの名無しさん :02/11/10 10:54
>>672
普通,
const char default_a_table[70][3?] = {
 "aa",
 "bb",
};
コンストラクタ
memcpy(a, default_a_table, sizeof(a));

675 名前:デフォルトの名無しさん :02/11/10 12:31
コンストラクタでクラス内で使用したい変数を new した際に、
new できずに返り値として NULL が返った場合どういった処理をすればよいのでしょうか?
クラスの使用者に安全に使ってもらうためにはどうしたらよいのでしょうか。
例外を投げたりして教えるのでしょうか?

676 名前:デフォルトの名無しさん :02/11/10 13:12
newは新規作成できない場合std::bad_allocを投げますが…
NULLで判断するのは一昔前の話では

677 名前:デフォルトの名無しさん :02/11/10 15:14
VCを使っているのですが、出力結果を標準出力から
テキストファイルに変更するにはどうしたらいいでしょうか

678 名前:デフォルトの名無しさん :02/11/10 15:59
freopen(stdout, "ファイル.txt", "wt");

679 名前:677 :02/11/10 16:19
"wt"というのは何ですか。
すいませんが教えてください。

680 名前:デフォルトの名無しさん :02/11/10 16:26
>>679
VC使ってるならコードをコピってF1押せ。
特定の関数のフラグなんか、2chで聞くよりヘルプ見たほうが早いだろ

681 名前:デフォルトの名無しさん :02/11/10 19:33
(・∀゚) <っ…コメントネェヨ

682 名前:デフォルトの名無しさん :02/11/10 21:13
2つ構造体同士のコピーについて質問です。
typedef struct { // 1
char * tekitou; // 2
}DATA; // 3
DATA * original; // コピー元 4
DATA * copy; // コピー 5

original = new DATA; // 6
/* 本来データはあらかじめ存在する値
ここでは適当に作っただけ */

char input[]="sage"; // 元の構造体を適当につくる 7
original->tekitou=(char *)malloc((strlen(input)+1)); // 8
strcpy(original->tekitou,"sage"); // 9

// original を copy にコピーする
copy = new DATA; // 10
copy->tekitou=(char *)malloc( ?????? ); // 11

11行目でも領域確保はどのようにしたらよいのでしょう?
strlen(original->tekitou) でも sizeof(original->tekitou) でもだめですよね。sage という文字数を判別するにはどーしたらよいのでしょうか?

683 名前:デフォルトの名無しさん :02/11/10 21:15
↑省略されて見るの面倒ですが、マジで困ってるのでどなたかおねがいします

684 名前:デフォルトの名無しさん :02/11/10 21:22
C++と全然関係ないない。sage

685 名前:デフォルトの名無しさん :02/11/10 23:04
>>676
ありがとうございました。
new(nothrow) すると例外投げずにできるんですね。

686 名前:デフォルトの名無しさん :02/11/11 16:54
失礼します。相談したいです。

構造体のメモリ確保に関しての質問です。
プログラム開始後、
自分の指定した数だけ構造体を作りたい時はどうすればよいですか?


例えば
cout<<"データ数は?\n";
cin >> num;
などとした後

struct data{
double a[10000];
double b[10000];
double c[10000];
}data,*datap;
datap = &data;
このような構造体をnumの数だけ確保したいとき、
どうしたらよいでしょうか?

datap = new data ???????;
↑??????らへんの書き方がよくわかりません。

どなたかよろしければアドバイスお願いします。

687 名前:デフォルトの名無しさん :02/11/11 17:27
クラス名とインスタンス名が同じ名前になってるぞ。

struct Data{...
}data,*datap;
datap = new Data [num];
delete [] datap;


688 名前:デフォルトの名無しさん :02/11/11 17:51
>>687
書き間違えていましたね。
アドバイスありがとうございましたー

689 名前:686 :02/11/11 18:57
686の者です。
すいません、書き方間違えていました。
numの分だけ構造体メンバーの配列を増やしたいでした。
つまり
struct Data{
double a[10000*num];
double b[10000*num];
double c[10000*num];
}data,*datap
という感じで。
ただ、この形じゃあコンパイルがとおらないので、
どなたかよい方法教えていただけませんか?

690 名前:デフォルトの名無しさん :02/11/11 19:00
素直にvector使っと毛

691 名前:デフォルトの名無しさん :02/11/11 20:00
>>689

struct Data{
Data(int num){
a=new double[10000*num];
b=new double[10000*num];
c=new double[10000*num];
}
double* a;
double* b;
double* c;
...

692 名前:686 :02/11/11 20:04
>>690
さきほどvectorについて調べました。
まだ初心者なのでなかなか難しそうです。
その方法しかなければ勉強するしかないのでがんばります。

693 名前:686 :02/11/11 20:06
>>691
おー!ありがとうございます。
早速試してみます。

694 名前:デフォルトの名無しさん :02/11/11 23:04
文字列と整数をキーにしたオブジェクトを溜め込むのにmapを使って、

struct key {
string name;
int num;
};

typedef map<key, ClassName> ClassTable;

このような宣言ってありですか?
とくにstruct keyのここでの使いっぷりってどうなんでしょ?


695 名前:デフォルトの名無しさん :02/11/11 23:08
keyには適切な比較演算子、代入演算子、コピーコンストラクタが
定義されていればなんでもいいんじゃなかろうか。

696 名前:デフォルトの名無しさん :02/11/12 00:46
>>694
> とくにstruct keyのここでの使いっぷりってどうなんでしょ?

1. Assignable, すなわち Key 型の変数 t, u に対して t = u を実行すると、
 t と u が等しくなり、その式の戻り値は Key& 型である。

2. map テンプレートクラスの第三引数 Compare (デフォルトでは std::less<key_type>) に
 よって、厳密な弱い順序づけ (strict weak ordering) がなされる。すなわち
 Key 型の変数 t, u は

  t と u が等しい <=> !Compare(t, u) && !Compare(u, t) が真

 である。

これが条件。

ダメな例を挙げると const int みたいに代入不可能であるとか、auto_ptr
のように代入後の値が異なってしまうもの。それから Compare を

 t <= u

みたいな定義にするのもダメ。これだと

 !Compare(t, t) && !Compare(t, t) = !(t <= t) && !(t <= t) =
 !ture && !true = false && false = false

となってしまい、2 の条件に反するから。

697 名前:686 :02/11/12 13:39
>>691
ちょっとうまくできません。
これはメモリを確保するために、
構造体のポインタをこう定義しているのですか?

構造体メンバの動的配列のやり方って無理なんですかね。。。

698 名前:デフォルトの名無しさん :02/11/12 13:46
その num の値はどうやって供給するつもりなんよ?
num が const なら >>689 のままでいけるし、変数なんだったら
>>691 のようにするしかあるめぇ。


699 名前:デフォルトの名無しさん :02/11/12 13:48
686

 何 が や り た い ん で す か ?

700 名前:686 :02/11/12 13:54
>>698
numはcin>>numで供給するつもりでした。
>>699
もうちょっと勉強します。

701 名前:686 :02/11/12 13:57
本日はここまでです。
お疲れさまでした!


702 名前:デフォルトの名無しさん :02/11/12 14:06
:-)


703 名前:デフォルトの名無しさん :02/11/12 16:06
template <std::size_t Size>
struct data{
double a[Size];
double b[Size];
double c[Size];
};

data<num> data_instance;

…ってnumは変数か。std::vector<>使えばいいんでないの?

704 名前:デフォルトの名無しさん :02/11/12 17:42
クラスを継承するときの関数のオーバーロードについて質問させて下さい。

下のようなクラスAとその継承クラスBを作りました。
Bのインスタンスを作成したとき、
BのコンストラクタではB::func(theta)を用いて処理を行って欲しいのですが
なぜかA::func(theta)が呼び出されてしまうようです。
どのように書けば意図した動作をしてくれるのでしょうか…?


class A{
protected:
virtual void func(double theta)=0;
public:
A(double theta){func(theta)を使った処理}
};

class B:public A{
protected:
virtual void func(double theta){オーバーライドさせたい処理}
public:
B(double theta):A(theta){;}
};

705 名前: ◆hMJAPH9PWA :02/11/12 17:48
コンストラクタ内では仮想関数は呼べないはずだよ。
A*を返す擬似コンストラクタを使えばいい。

// こんな感じで。
A* A::create(){
A* self = new A;
func(...);
return self;
}

706 名前:デフォルトの名無しさん :02/11/12 18:05
mapの値に抽象クラスを入れるのは無理?

707 名前: ◆hMJAPH9PWA :02/11/12 18:15
普通に無理でしょ…値が作れたら抽象クラスじゃなくなっちゃうよ。
抽象クラスのポインタなら行けるだろうけど。


708 名前:デフォルトの名無しさん :02/11/12 20:03
vector<int> *vect;
ってなんなの?

709 名前:デフォルトの名無しさん :02/11/12 20:09
>>708
vectはstd::vector<int>を指すポインタ。

710 名前:デフォルトの名無しさん :02/11/12 20:09
>>880
qsort()ならsearch.hをインクルードしてるから大丈夫だよ。

711 名前:デフォルトの名無しさん :02/11/12 20:11
>>710は誤爆です。ス マ ソ

712 名前:デフォルトの名無しさん :02/11/12 20:22
>>708
vector<int>objectを将来指すであろうpointerのdeclaration。

713 名前:デフォルトの名無しさん :02/11/12 21:34
>>708の宣言のあと、

vect = new vector<int>;
vect->push_back(1);

とかでいいんですか?
使い方は。

714 名前:デフォルトの名無しさん :02/11/12 21:37
>>713
STLスレッドにおいで。議論がされてるよ。

715 名前:デフォルトの名無しさん :02/11/12 21:45
>>714
stlスレ見ました。
誘導ありがとうございますた。

716 名前:デフォルトの名無しさん :02/11/13 09:45
下みたいに、参照に null pointer を代入するのって、規格上許されてる?
g++ だとコンパイルできて期待通り動くんだけど、実装依存なんてことも
あるんでしょうか。

#include <iostream>
int main()
{
int& ri = *((int*)0);
if (&ri == 0) {
std::cout << "null reference" << std::endl;
}
}

717 名前:デフォルトの名無しさん :02/11/13 09:58
*((int *)0);

これってポインタなのか?
ポインタを間接参照しているようにみえるが。

718 名前:716 :02/11/13 10:10
>ポインタを間接参照しているようにみえるが。
そう。まさしくそう見えるので不安なわけです(w

719 名前:デフォルトの名無しさん :02/11/13 10:32
規格はどうだか知らないけど、VC のリスティング見ると内部的にポインタに
なってるみたいだね。

int *p = (int*)0;
if (p == 0) { ...

と同じ処理になってる。
*p や ri を使おうとすると、たちどころにアクセス違反になる。

720 名前:デフォルトの名無しさん :02/11/13 10:48
C++3rdの5.5には初期化子は左辺値であればいいみたいなことが
書いてあるけども

721 名前: ◆hMJAPH9PWA :02/11/13 11:01
*((int*)0)はnull pointerを参照している事にはならないんだろうか。

722 名前:716 :02/11/13 11:42
720> 初期化子は左辺値であればいいみたいな
つまりは、&(*((int*)0)) が有効な式になるかどうかってことかな。

723 名前:720 :02/11/13 12:22
ということだと思うんですけども。
単項の * って左辺値つくり出んじゃなかったっけ、、

724 名前:デフォルトの名無しさん :02/11/13 12:32
参照への代入に限って違うとか。

725 名前:デフォルトの名無しさん :02/11/13 12:59
int main()
{
int &r = *((int*)0); //平気
int c = *((int*)0); //だめぽ
int &rr = r; //こっからダミー
int cc = c;
return 0;
}


726 名前:デフォルトの名無しさん :02/11/13 18:48
castは新しいのをね。

727 名前:デフォルトの名無しさん :02/11/13 22:47
みなさん、コンストラクタから例外投げてますか?

今までは「絶対に」投げてはいけないと思っていましたが、例外を投げても良い場合もあるんだという考え方もあるようで、

どっちが正しいのかよくわかんない。。。

 ttp://www.microsoft.com/japan/msdn/library/default.asp?url=/japan/msdn/library/ja/jpdndeepc/htm/deep02172000.asp

を読みましたが良くわかりませんでした。誰か頭の良い人、フォローしてください。


728 名前:デフォルトの名無しさん :02/11/13 22:49
exceptional C++ を読みましょう >>727



729 名前:デフォルトの名無しさん :02/11/13 22:52
exceptional C++ は買ったが読めないす。誰かフォローして。(今日はもう終電なので帰ります)


730 名前:デフォルトの名無しさん :02/11/13 22:53
>>727
そのページに
> 例外をスローすべき十分な理由があるなら、進んでその例外を
> スローして、それを文書化すればよいのです。例外をスロー
> するのが当然の場面で、例外のスローを回避する方法を
> 発明する必要はありません。複雑にすることで、制限された
> バージョンのクラスを誰かが誤用する危険よりもかえってひどい
> 保守の悪夢が生まれてしまいます。
と書いてあるではないか。

というか、あなたが何故『「絶対に」投げてはいけない』と思うのかが謎なのだが。

731 名前:デフォルトの名無しさん :02/11/14 00:29
main()
{
  const unsigned N = 1;
  try{ for(;;) new int[N]; }
  catch( ... ){}
}

↑のプログラムが、Aborted(core dumped) になってしまいます。
なにが起こっているんでしょうか?

N = 1024 にしたら無言で終了しました。(これが期待の動作)
環境は、 cygwin g++-3.1.1 です。

732 名前:デフォルトの名無しさん :02/11/14 00:36
後始末の処理にもヒープメモリを必要とするからじゃないの?

733 名前:731 :02/11/14 01:25
ちょっと調べてみたんだけど、
漏れの結論は
「std::bad_allocを投げるのに動的メモリを必要とするようなg++の実装がクソ」
になりました。
・・・いいのかなぁ?

734 名前:デフォルトの名無しさん :02/11/14 09:29
>>727
例外安全にしたければ Pimpl パターンを使えってこった。


735 名前:デフォルトの名無しさん :02/11/14 09:41
>>734
いつも思うんだが・・
pimplってどう発音してる? ぴーいんぷる? ぴんぷる?


736 名前:デフォルトの名無しさん :02/11/14 10:00
C++ FAQでは、コンストラクタでスローしろと書いてあったような記憶がある…

737 名前:デフォルトの名無しさん :02/11/14 10:11
>>735
漏れはぴーいんぷる。

>>736
漏れも C++ FAQ でそういう話見た気がする。


738 名前:デフォルトの名無しさん :02/11/14 10:38
デストラクタでthrowする香具師はドキュソ。とりあえずそれだけでいい
んじゃないすか。>727



739 名前:デフォルトの名無しさん :02/11/14 11:02
>>735
俺はぴーいんぷり。

>>727
普通に投げる。何か問題ある?

740 名前:デフォルトの名無しさん :02/11/14 14:22
>>727
例外は、戻り値がない コンストラクタ で一番威力を発揮するもんだろうが。
>>735
ぴーいんぷる

741 名前:デフォルトの名無しさん :02/11/14 14:38
>>738
前から思ってたんけど 香具師 をきちんと辞書で調べたか?

742 名前:デフォルトの名無しさん :02/11/14 15:03
>741
既出の読みはガイシュツではない。とか言い出す予感

743 名前:デフォルトの名無しさん :02/11/14 15:15
2ちゃん用語でウンチク語りだすのか(w
恥ずかしいなぁ。まあ2ちゃん用語自体恥ずかしいが。

744 名前:困っています :02/11/14 18:34
マウスでドラッグ選択した部分の描画を拡大縮小する良い方法ありませんか?!参考になるものでも結構です。
お願いします。


745 名前:デフォルトの名無しさん :02/11/14 18:38
StretchBlt()


746 名前:デフォルトの名無しさん :02/11/14 21:33
>>743
2ちゃん内では別に恥ずかしくない

747 名前:デフォルトの名無しさん :02/11/14 21:38
むしろ 「(w」 りの方が恥ずかしい

748 名前:デフォルトの名無しさん :02/11/14 21:51
り?

749 名前:デフォルトの名無しさん :02/11/14 21:58
自分の為のライブラリ、作ってますか?

750 名前:747 :02/11/14 21:59
漏れも恥ずかしい


■過去ログ置き場に戻る■ 1- 前250 次250 最新50
DAT2HTML 0.33f Converted.