関数のエラー

[戻る]
wer 2002/12/13(金) 02:37:35
error C2091: 関数は関数を返せません。
error C2511: 'hyouzi' : オーバーロードされたメンバ関数が '<Unknown>' にありません。
cl.exe の実行エラー

上のようなエラーが出るのですが関数は次のように書きました。

void CKteiView::hyouzi(CDC* pDC)(int x1[],int y1[],int a,int b,int c,int d,char 
e[])
{
    if(d==0)pDC->TextOut(x1[a],y1[a],e);
    if(d==1)pDC->TextOut(x1[a],y1[a]-c,e);
       if(d==2)pDC->TextOut(x1[a]-b,y1[a]-c,e);
    if(d==3)pDC->TextOut(x1[a]-b,y1[a],e);
    return(0);
}

wood 2002/12/13(金) 04:54:08
ヘッダの方はどうなっているの?

RAPT 2002/12/13(金) 04:56:10
こんばんは、RAPTです。

・CKteiViewクラスのメンバ関数に、hyouzi という関数が宣言されていない。
・void 型の関数なのに、return(0); と書かれている。

# 個人的には、return 文は関数でも、マクロでもないので、return(0);
# ではなく、return 0; と書いて欲しいものだなぁ、と思っています。

Windows98/VC++6.0std/SDK-may2002/ATL3.0/WTL7.0

渋木宏明(ひどり) [E-Mail] [HomePage] 2002/12/13(金) 05:11:54
>void CKteiView::hyouzi(CDC* pDC)(int x1[],int y1[],int a,int b,int c,int 
d,char e[])

は、ごく単純に

void CKteiView::hyouzi(CDC* pDC, int x1[],int y1[],int a,int b,int c,int 
d,char e[])

とするべきなのでは?

YuO [E-Mail] 2002/12/13(金) 11:49:01
> void CKteiView::hyouzi(CDC* pDC)(int x1[],int y1[],int a,int b,int c,int d,char e[])

これは,typedefを使ってわかりやすく書くと,
typedef void F(int [], int [], int, int, int, int, char []);
F CKteiView::hyouzi(CDC* pDC);
として扱われてしまいます。
Fはintの配列を二つ,intを四つ,charの配列を一つを引数としてこの順で受け取り,
値を返さない関数という型です。

本当にFを返したいのであれば,
F * CKteiView::hyouzi(CDC* pDC);
としないといけません。

まぁ,プログラムを見る限り,渋木さんの書かれたとおりだと思います。

wer 2002/12/13(金) 11:52:11
ご返答ありがとうございます。
渋木宏明(ひどり)さんが書いてくれたとおりにするとエラーが減りました。

error C2660: 'hyouzi' : 関数が不正な 7 個の実引数をともなって呼び出されました。

これはどういったエラーなのでしょうか。

soto 2002/12/13(金) 11:55:46
MSDNでC2660を検索してみれば分かるとおり
間違った実引数を与えて関数を呼び出しているのだと思います。
もう一度渡している値と引数の型などを見比べてみてはいかがでしょうか?

wer 2002/12/13(金) 12:02:11
すいません 関数の渡し方は

hyouzi(x1,y1,a,b,c,d,e);

でいいのでしょうか?

soto 2002/12/13(金) 12:24:14
x1,y1,a,b,c,d,e
はどのように宣言しているのでしょうか?
それぞれの「型」と「関数に渡す前に代入している値」を教えてください

wood 2002/12/13(金) 12:29:31
>void CKteiView::hyouzi(CDC* pDC, int x1[],int y1[],int a,int b,int c,int 
d,char e[])
だと
>hyouzi(x1,y1,a,b,c,d,e);>CDC* pDC
の引数が足らなくないですか

wer 2002/12/13(金) 12:33:57
int x1[100],y1[100],a,b,c,d;
char e[100];
a=0;    b=70;    c=20;
x1[a]=385; y1[a]=78;
d=1;
sprintf(e,"場所");
hyouzi(x1,y1,a,b,c,d,e);

このようになっています。

wer 2002/12/13(金) 12:47:49
hyouzi(CDC* pDC,x1,y1,a,b,c,d,e);
こうするとエラーが出ます。
やはりYuOさんが書いてくれたように
しなくてはならないのでしょうか?

YuO [E-Mail] 2002/12/13(金) 12:59:18
> hyouzi(CDC* pDC,x1,y1,a,b,c,d,e);
> こうするとエラーが出ます。

関数の呼び出しについて,ちゃんとわかっていますか?
CDCへのポインタはウィンドウなどからきちんと取得してください。

wer 2002/12/13(金) 14:52:48
>関数の呼び出しについて,ちゃんとわかっていますか?
 hyouzi(x1,y1,a,b,c,d,e);
 でよかったですよね?
>CDCへのポインタはウィンドウなどからきちんと取得してください。
void CKteiView::hyouzi(CDC* pDC)(int x1[],int y1[],int a,int b,int c,int d,char 
e[])

このようなとき取得の仕方はどうすればよいのでしょうか?

PAI 2002/12/13(金) 15:57:19
>hyouzi(x1,y1,a,b,c,d,e);
> でよかったですよね?

よくないって、第一引数は CDC* なんでしょ。

>>CDCへのポインタはウィンドウなどからきちんと取得してください。
>void CKteiView::hyouzi(CDC* pDC)(int x1[],int y1[],int a,int b,int c,int d,char
e[])
>
>このようなとき取得の仕方はどうすればよいのでしょうか?

その関数を呼び出す側で、なんとかしてデバイスコンテキストを取得する。としかいえない。

sugar 2002/12/13(金) 16:21:59
>void CKteiView::hyouzi(CDC* pDC)(int x1[],int y1[],int a,int b,int c,int d,char
e[])
>
この宣言だと、

>error C2091: 関数は関数を返せません。
>
が出ちゃうんですよね?
関数は、「関数へのポインタ」なら返せますが、
この宣言だと、返してるのはポインタではないということでは?
YuOさんの最初の書き込み、とても重要だと思いますが。

結局CKteiView::hyouziという関数は、いくつの引数を必要とすると思いますか?

PAI 2002/12/13(金) 16:30:23
ごめんなさい、私の書き込み語弊がありますね。
関数内でデバイスコンテキストとっても別にかまわないわけだし。

YuOさんのいう
>関数の呼び出しについて,ちゃんとわかっていますか?

は、
『C++のにおける関数呼び出しというものの機構を理解していますか?』
という意味なことは、わかりますか?

wer 2002/12/14(土) 11:37:19
>『C++のにおける関数呼び出しというものの機構を理解していますか?』
>という意味なことは、わかりますか?
いまいちわからないのですが

>関数内でデバイスコンテキストとっても別にかまわないわけだし。
デバイスコンテキストを取得するってゆうのはどのように
取得するのでしょうか。

渋木宏明(ひどり) [E-Mail] [HomePage] 2002/12/14(土) 13:34:43
> error C2660: 'hyouzi' : 関数が不正な 7 個の実引数をともなって呼び出されまし
た。

> これはどういったエラーなのでしょうか。

宣言と定義の記述に食い違いがあるんでしょう。

.h と .cpp ファイルの、houzi() 関数の記述(=引数など)を見比べてください。

まーおそらくは .h の方でしょう。

例)
--hoge.h--
class CHoge
{
protected:
  void houji(CDC* pDC,int x1[],int y1[],int a,int b,int c,int d,char e[]);
}
--hoge.h--

--hoge.cpp--
void CHoge::houji(CDC* pDC,int x1[],int y1[],int a,int b,int c,int d,char e[])
{
  // TODO: ここに処理を記述します。
}
--hoge.cpp--

PAI 2002/12/15(日) 02:09:27
ちょっと錯綜しちゃってますね。

まず
    関数っていうのは
        0個以上の引数を渡して、
        関数内の処理をして
        1個、もしくは0個の値を返す。
    というものである。
↑これはOK?

んで、
    関数は
        戻り値 関数名(引数並び);
    として宣言する。
    
    呼び出すとき、引数は宣言時の型か、
        それへと暗黙に変換できる型の変数を宣言したとおりに渡す必要がある。
    関数の宣言と定義は違う。(ちょっと微妙な表現ですが)
    定義は宣言と同じシグネチャで行わなければ、オーバーロードとなる。
↑これはOK?

さらに
    C++ではクラス毎にメンバ関数というものを作ることができ
    ヘッダで宣言したものを実装ファイルで定義する(ことができる)。
    このとき、クラス宣言時に宣言したシグネチャと違うものは定義できない。
↑これはOK?


以下、ここまではわかってるものとしてすすめます。
ここまでがわかっていないようでしたら入門書をもう一度読まれることをお勧めします。


で、

>void CKteiView::hyouzi(CDC* pDC)(int x1[],int y1[],int a,int b,int c,int 
d,char e[])

という関数ですが、これは
    戻り値 関数名(引数並び);
になってませんよね。

でもコンパイラから見るとこれは

    戻り値 関数名(引数並び);

になっていて、まぁいろいろあって
    
    CKteiViewクラスのhyouziという名前の
    CDC*型の引数をとって
    「int[]2つ, int4つ、char[]1つをうけて値を返さない関数 」
    を返す関数

という意味になってしまいます

C++では関数を返すことはできないのでこれはエラーになります。
関数へのポインタを返すことはできるのですが、かなり込み入ったことをするのでなければ
普通そういうことはしません。

werさんは関数、あるいは関数ポインタを返す関数を作成したかったわけではありませんよね?
以下関数を返したかったわけではないと仮定して話を進めます。
関数を返したかったのであれば
・・・すみませんが『10年早いんだYO!!』とだけ言っておきます。


ここまできてやっと本題らしいことに入れますが、

引数については、woodさん、渋木宏明(ひどり) さん諸氏のおっしゃるとおりです。
本当に必要な引数を宣言し、同じシグネチャで実装し、その型で呼んでください。


デバイスコンテキストは、Windowsの表示デバイスを抽象化するもののため
どこに表示したいかによって異なります。

CKteiViewがCViewの派生クラスであるとして、そのViewのクライアント領域でいいのであれ
ば、
CWnd::GetDC(),もしくはCClientDCを使用するといいでしょう。

wer 2002/12/15(日) 02:25:55
ご返答ありがとうございます。
実際やりたかったことはOnDraw関数に

  if(d==0)pDC->TextOut(x1[a],y1[a],e);
    if(d==1)pDC->TextOut(x1[a],y1[a]-c,e);
    if(d==2)pDC->TextOut(x1[a]-b,y1[a]-c,e);
    if(d==3)pDC->TextOut(x1[a]-b,y1[a],e);
を書いていたんですがこれを違う関数を作り
表示させたかったんです。

wer 2002/12/15(日) 10:50:44
[[解決]]
皆様すいませんでした。
CClientDCをつかい表示できました。
ありがとうございました。

古いスレッドには追加発言できません。