• 締切済み

ヘッダファイルを使わずに定義する方法

新しい関数を使ったソースを古いOSでコンパイルすると、外部シンボル...Aが未解決になります。 ヘッダファイルでその関数のプロトタイプを書くとコンパイル可能になると思いますがヘッダファイルを使わずに*.cppにプロトタイプを書くようなことは可能ですか? __declspec(import) DWORD Win7OnlyEx(LPTSTR);

みんなの回答

  • wormhole
  • ベストアンサー率28% (1619/5654)
回答No.3

プロトタイプ宣言をしたところで リンク時の外部シンボルの未解決は直りませんよ。 プロトタイプ宣言は「こういう関数がありますよ」というだけで その関数の実態があるかないかはまた別の話です。 プロトタイプ宣言で関数の実態まで勝手に作ってくれる なんてことはありません。

  • hitomura
  • ベストアンサー率48% (325/664)
回答No.2

それよりも対象のOSで使えない関数は使わないとか、VC++なら_WIN32_WINNT や WINVERマクロを設定し、その値を見て処理を切り分けるとかにしたほうがいいように思えます。 また、例示の Win7OnlyEx の場合、 DWORD MyWin7OnlyEx(LPTSTR p) { #if defined(WINVER) && WINVER >= 0x601  return Win7OnlyEx(p); #else  return 0; // あるいは何らかのエラー値を返す #endif // defined(WINVER) && WINVER >= 0x601 } とラップして、Win7OnlyEx の代わりにこの関数を呼び出すようにするという手があります。

参考URL:
http://homepage1.nifty.com/herumi/prog/gcc-and-vc.html#GOOD_MACRO
回答No.1

可能/不可能?だけを考えれば、ヘッダファイル(*.h)はソースファイル(*.c/*.cpp)にインクルードして使用するものですから、ソースファイルにその内容を直接記述することは可能です。しかし、何故プロトタイプ宣言がヘッダーファイルに分離されているかを考えれば、プロトタイプ宣言をソースファイル内に書くことはやらないほうが賢明でしょう。 問題点(外部シンボルの未解決)に対して対策(プロトタイプ宣言のソースファイルへの記述)が正しくないように思われます。 コンパイラのバージョンによって処理を変更する場合、コンパイラの定義済みのマクロによって条件コンパイルを行うようにヘッダ/ソースファイルを記述すべきです。 たとえばVisuall C++ではコンパイラのバージョン番号として _MSC_VER が定義されているので、条件コンパイルに使用できます。 #if _MSC_VER < 1500 // VC++ 2005(?)以下 ...(対象のバージョン以下のの記述) #else ...(対象のバージョン以上のの記述) #endif

関連するQ&A

  • 自作ヘッダファイルについて (C言語)

    自作ヘッダファイルについて質問なのですが、ヘッダファイルには外部変数や関数のプロトタイプ宣言を記述しますよね?では関数の実装はどこで行ったらいいのでしょうか?回答よろしくお願いします。

  • 複数ファイルによる共通の外部変数定義について

    初歩的な質問なのですが、今各関数をファイルごとに分けて記述しようとしています。 ここで詰まっているのでできればご教授お願いします ファイル構成は プログラムファイル main.cpp sub.cpp ヘッダーファイル  myheader.h(main.cppとsub.cpp両方でインクルード) ヘッダーファイルには両方のプログラムファイルで使う変数が定義してあります。 それでmain.cppとsub.cpp両方で同じ変数を使いたいのですがコンパイルエラーが発生してしまいます。 内容はsub.obj側で「i(共通のループカウンタ)はmain.objですでに定義されています」というものです。 とにかく私のやりたいことはヘッダーに外部変数を定義して両方のプログラムファイルで使いたいというものです。 もしかしたらファイルを分けるにも何か設定が必要なのでしょうか? 私はただ[プロジェクト]→[プロジェクトに追加]→[新規作成]でソースファイルを作っているだけなんですが・・・ 上記の状態を回避する方法はあるのでしょうか?

  • 複数のCのみファイルをリンクし一本の実行ファイルまたはDLLを作成する方法

    いつもお世話になっています。 現在、それぞれCのみで作成したファイルをリンクし、ひとつのDLLファイルまたはEXEファイルを作成したいのです。 作成方法はWin98,MS-VisualStudio6.0です。 今まで調べたやりかたでWin32Dynamic・・・ で「シンボルをエクスポートする」で行った場合、 DLLmainが「CPP」になってしまいました。 DLLmainをCで作成したい場合は、やはり空の「シンボルを作成する」にしなければいけないのでしょうか? 網羅する場合はプロトタイプ宣言を外部ヘッダファイルに記述するのでしょうか? そのサンプルと言うか、詳しく掲載しているサイトがあったら教えてください。 初心者なので、MSDNの説明だと理解に苦しみます。

  • 質問させてください。

    質問させてください。 vista 32bit で VisualStudio2008pro を使い開発をしています。 ヘッダーファイルもインクルードし、 libファイルもリンクしているのですが、 下のエラーがなくなりません。 error LNK2001: 外部シンボル ""extern "C" int __stdcall aaaa(int,unsigned char *,unsigned char *)" (?aaaa@@$$J212YGHHPAE0@Z)" は未解決です。 DLLをインポートするヘッダーでは、 __declspec(dllimport)を使いインポートしています。 インポートのヘッダーは、64bit でも使っていて、 そちらはちゃんとコンパイルは通ります。 色々調べまわって、設定も色々変えてみたのですが 全然変わらないです。 本当に困っています。 わかる方がいられれば是非ご教授願います。

  • ヘッダーファイルについて

    //DMusic7Ex.h あるプログラムを解析しています。 //コンパイラ設定 //多重定義防止 #pragma once //ファイルインクルード #include <dmusicc.h> #include <dmusici.h> //型定義 typedef IDirectMusicPerformance* LPDIRECTMUSICPERFORMANCE; typedef IDirectMusic* LPDIRECTMUSIC; typedef IDirectMusicLoader* LPDIRECTMUSICLOADER; typedef IDirectMusicSegment* LPDIRECTMUSICSEGMENT; //関数プロトタイプ 1・DMusic7Ex.cppを作らず他の関数で、このヘッダーファイルをインクルードする手法は一般的なのか? 2・なぜ関数プロトタイプを記述しないで、このタイプ宣言を他のファイルで使用するのは一般的なのか?

  • DLLとインポート、エクスポート

    環境 Microsoft Visual C++ DLLはWin32 Dynamic-Link Library ExeはWin32 Application で作成しています。 DLLにメッセージボックスを表示するのみの処理の関数があり。 Exe側でその関数を使用したいだけです。 DLLのヘッダファイルにエクスポートしたい関数を _declspec(dllexport) void exportmain(); としています。 Exeではインポートを __declspec(dllimport) void exportmain(); としています。 プロジェクト⇒設定⇒リンクにlibファイルの設定もしています。 dll、libファイルの場所も問題ないと思います。 しかし、ビルドすると「外部シンボル~~未解決です」とエラーがでてしまいます。なにか原因がわかるかたおりましたら、ご教授お願い致します。

  • 他の.CPPファイルに定義した関数を呼び出す方法について

    新規作成したプロジェクトに、 以前自分が作成した.cppファイルと.hファイルを そのまま使えないかと考えています。 (※仮にそのファイルの名前を "define.cpp" "define.h" とします) プロジェクトに新規ファイル main.cpp を作成して、 define.hをインクルードし、 以下のようなテストのプログラムを組みました。 ・../util/define.cpp---------------------- #include <iostream> #include "define.h" void test(){ std::cout<<"test."<<std::endl; } ・../util/define.h------------------------ #pragma once void test(); ・main.cpp---------------------------- #include "../util/define.h" int main(){  test();  return 0; } 上記のソースを VisualC++7.0 でビルドすると、 main.cppの3行目で以下のようなエラーが出ました。 > LNK2019: 未解決の外部シンボル "void __cdecl test(void)" が関数 _main で参照されました VisualC++で「既存項目の追加」という項目より、 実体の定義されたdefine.cppをプロジェクトに追加していないため 当然といえば当然なのですが・・・ C言語でいうところの<stdio.h>等みたいに、 わざわざプロジェクトにCPPファイルを追加しなくても 関数を呼び出せるようには出来ないのでしょうか? 全ての関数と処理をヘッダーファイルに記述すると解決ですが 物凄く見辛いのでそれは避けたいのです。 また、色々なPC間で使っているため(学校のPCなので)、 ツール自体のプロパティを弄らない方法があるのでしたら、 多少面倒でもそちらの方が好ましいです。 追加する方法があるかどうか、 あればその方法をご存じでしたら教えていただければ嬉しいです。 よろしくお願いします。

  • ポインタによる包含&ヘッダにincludeしない、 場合でtemplateの定義に…

    class Bの宣言をしているヘッダ中で class A; を、前方宣言し、そのポインタだけを持たせ、ソースファイルのほうにclass Aの中身が分かるように、#includeして、ソースファイルに関数の実装やstatic変数の定義を書いていた、とします。 しかし、templateを使う関数についてはコンパイル時に解決できないといけないので、それだけはヘッダに持ってきました。 その時 includeが一切書かれていない、class Bのヘッダ内において class Aのメンバを参照するようなコードを書いたとき クラス外、クラス内、いずれに書いても 正常にコンパイルできました。 通常の関数では当然無理なので、もともとtemplateがコンパイル時解決を強要するものなのでそういう仕様にしててくれてると考えられますが 1.これは、C++の標準仕様でしょうか?それとも処理系依存でしょうか? あと、templateに関して 2.特殊化ならソースにかけるのは標準仕様でしょうか?それとも処理系依存でしょうか?

  • クラスのメンバ関数を別ファイルで定義したときのバグ

    C++ においてヘッダファイルで宣言したクラスのメンバ関数を別のソースファイルで定義して、コンパイルするとうまくいきません。エラーは出ないのですが、同名の何もしない関数としてコンパイルされているようなのです。クラスのメンバ関数を宣言したのと同じヘッダに書くとちゃんとコンパイルされます。 どうしてそうなるのか、いまいち原因がわかりません。

  • JAVAで外部ファイルをインクルード

    JAVAの初心者です。 Cのヘッダファイルみたいに、自分で作った外部ファイルをインクルードするには import 文を使ってメインのクラスの前にいれれば良いとおもうのですが、その 認識で間違ってないでしょうか。 また、そのファイルは、あらかじめコンパイル済みである必要があるのか、読み込み側となるソースファイルと同じディレクトリにおいておけば単純にコンパイルが済むのか。 説明が伝わりにくいかと思いますが、どうかよろしくお願いします。

    • ベストアンサー
    • Java

専門家に質問してみよう