前提・実現したいこと
C++(MFC)でsqliteをDLLとして読み込んで使いたいです。
DLLの読み込み処理をクラスにまとめてヘッダファイル(.h)に書いた際は動作しましたが、
そのクラスのコンストラクタの実装を.cppに分割したところコンパイルが通らなくなりました。
開発環境は次の通りです
- Windows8.1(64bit)
- VisualStudioCommunity2017
- MFCアプリケーション(ダイアログベース)
- SQLite version 3.27.1 こちらを元にDLLを読み込む処理を書いた
該当のソースコード
ダイアログにはボタンが一つあり、それが押されたときにsqliteのDLL読み込んで.db
ファイルを作ります
sqliteを扱うクラスはSaver
という名前でsaver.h
にクラス定義、saver.cpp
にコンストラクタの実装、と分割したいと考えています。
saver.h
c++
1#pragma once 2 3#include "sqlite3.h" 4#include "stdafx.h" 5 6 7// sqlite3.dll内関数ポインタ型定義 8typedef int(__cdecl * pOpen)(char *, sqlite3 **); 9typedef int(__cdecl * pExec)(sqlite3 *, const char *, sqlite3_callback, void *, char **); 10typedef int(__cdecl * pGetTable)(sqlite3 *, const char *, char ***, int *, int *, char **); 11typedef int(__cdecl * pFreeTable)(char **); 12typedef int(__cdecl * pClose)(sqlite3 *); 13 14class Saver { 15 16 17 18public: 19 Saver(); 20 21 22public: 23 24 // 関数ポインタ変数 25 pOpen sqlite3_open; 26 pExec sqlite3_exec; 27 pGetTable sqlite3_get_table; 28 pFreeTable sqlite3_free_table; 29 pClose sqlite3_close; 30 31 32 HINSTANCE hDll; 33 sqlite3 *db; 34 char *err; 35 char **result; 36 int row, col; 37 CString str; 38 39};
saver.cpp
c++
1#include "saver.h" 2#include "stdafx.h" 3#include <windows.h> 4Saver::Saver(){ 5 6 AfxMessageBox(_T("saver constructed")); 7 // sqlite3.dllをロード 8 hDll = LoadLibrary("sqlite3"); 9 if (hDll == NULL) { 10 FreeLibrary(hDll); 11 AfxMessageBox(_T("dll cant be loaded.")); 12 return; 13 } 14 15 16 // sqlite3関数のアドレスを取得 17 sqlite3_open = (pOpen)GetProcAddress(hDll, "sqlite3_open"); 18 sqlite3_exec = (pExec)GetProcAddress(hDll, "sqlite3_exec"); 19 sqlite3_get_table = (pGetTable)GetProcAddress(hDll, "sqlite3_get_table"); 20 sqlite3_free_table = (pFreeTable)GetProcAddress(hDll, "sqlite3_free_table"); 21 sqlite3_close = (pClose)GetProcAddress(hDll, "sqlite3_close"); 22 23 24 25 // データベースファイルを作成 26 sqlite3_open("test.db", &db); 27 28 // テーブル作成 29 sqlite3_exec(db, "create table test(num integer,name string);", NULL, NULL, &err); 30 // データを格納 31 sqlite3_exec(db, "insert into test values(1,'test1');", NULL, NULL, &err); 32 33 34 // データベースファイルを閉じる 35 sqlite3_close(db); 36 37 38} 39
memoDlg.cpp
文字数が足りないので抜粋です。
デフォルトの状態からボタンを追加しており、ヘッダのインクルードとボタン押下時のクラスを実体化を追加しています。
c++
1 2// memoDlg.cpp : 実装ファイル 3// 4 5#include "stdafx.h" 6#include "memo.h" 7#include "memoDlg.h" 8#include "afxdialogex.h" 9 10#include "saver.h" 11
c++
1void CmemoDlg::OnBnClickedadd() 2{ 3 // TODO: ここにコントロール通知ハンドラー コードを追加します。 4 Saver sv; 5}
エラー
1>------ ビルド開始: プロジェクト: memo, 構成: Debug x64 ------ 1>saver.cpp 1>c:\users\master\desktop\memo\memo\saver.cpp(6): error C2653: 'Saver': 識別子がクラス名でも名前空間名でもありません。 1>c:\users\master\desktop\memo\memo\saver.cpp(6): error C4430: 型指定子がありません - int と仮定しました。メモ: C++ は int を既定値としてサポートしていません 1>c:\users\master\desktop\memo\memo\saver.cpp(10): error C2065: 'hDll': 定義されていない識別子です。 1>c:\users\master\desktop\memo\memo\saver.cpp(11): error C2065: 'hDll': 定義されていない識別子です。 1>c:\users\master\desktop\memo\memo\saver.cpp(12): error C2065: 'hDll': 定義されていない識別子です。 1>c:\users\master\desktop\memo\memo\saver.cpp(14): warning C4508: 'Saver': 関数に戻り値の型が指定されていません。戻り値を void 型と見なします。 1>c:\users\master\desktop\memo\memo\saver.cpp(19): error C2065: 'sqlite3_open': 定義されていない識別子です。 1>c:\users\master\desktop\memo\memo\saver.cpp(19): error C2065: 'pOpen': 定義されていない識別子です。 1>c:\users\master\desktop\memo\memo\saver.cpp(19): error C2146: 構文エラー: ';' が、識別子 'GetProcAddress' の前に必要です。 1>c:\users\master\desktop\memo\memo\saver.cpp(19): error C2065: 'hDll': 定義されていない識別子です。 1>c:\users\master\desktop\memo\memo\saver.cpp(20): error C2065: 'sqlite3_exec': 定義されていない識別子です。 1>c:\users\master\desktop\memo\memo\saver.cpp(20): error C2065: 'pExec': 定義されていない識別子です。 1>c:\users\master\desktop\memo\memo\saver.cpp(20): error C2146: 構文エラー: ';' が、識別子 'GetProcAddress' の前に必要です。 1>c:\users\master\desktop\memo\memo\saver.cpp(20): error C2065: 'hDll': 定義されていない識別子です。 1>c:\users\master\desktop\memo\memo\saver.cpp(21): error C2065: 'sqlite3_get_table': 定義されていない識別子です。 1>c:\users\master\desktop\memo\memo\saver.cpp(21): error C2065: 'pGetTable': 定義されていない識別子です。 1>c:\users\master\desktop\memo\memo\saver.cpp(21): error C2146: 構文エラー: ';' が、識別子 'GetProcAddress' の前に必要です。 1>c:\users\master\desktop\memo\memo\saver.cpp(21): error C2065: 'hDll': 定義されていない識別子です。 1>c:\users\master\desktop\memo\memo\saver.cpp(22): error C2065: 'sqlite3_free_table': 定義されていない識別子です。 1>c:\users\master\desktop\memo\memo\saver.cpp(22): error C2065: 'pFreeTable': 定義されていない識別子です。 1>c:\users\master\desktop\memo\memo\saver.cpp(22): error C2146: 構文エラー: ';' が、識別子 'GetProcAddress' の前に必要です。 1>c:\users\master\desktop\memo\memo\saver.cpp(22): error C2065: 'hDll': 定義されていない識別子です。 1>c:\users\master\desktop\memo\memo\saver.cpp(23): error C2065: 'sqlite3_close': 定義されていない識別子です。 1>c:\users\master\desktop\memo\memo\saver.cpp(23): error C2065: 'pClose': 定義されていない識別子です。 1>c:\users\master\desktop\memo\memo\saver.cpp(23): error C2146: 構文エラー: ';' が、識別子 'GetProcAddress' の前に必要です。 1>c:\users\master\desktop\memo\memo\saver.cpp(23): error C2065: 'hDll': 定義されていない識別子です。 1>c:\users\master\desktop\memo\memo\saver.cpp(28): error C2065: 'db': 定義されていない識別子です。 1>c:\users\master\desktop\memo\memo\saver.cpp(28): error C3861: 'sqlite3_open': 識別子が見つかりませんでした 1>c:\users\master\desktop\memo\memo\saver.cpp(31): error C2065: 'db': 定義されていない識別子です。 1>c:\users\master\desktop\memo\memo\saver.cpp(31): error C2065: 'err': 定義されていない識別子です。 1>c:\users\master\desktop\memo\memo\saver.cpp(31): error C3861: 'sqlite3_exec': 識別子が見つかりませんでした 1>c:\users\master\desktop\memo\memo\saver.cpp(33): error C2065: 'db': 定義されていない識別子です。 1>c:\users\master\desktop\memo\memo\saver.cpp(33): error C2065: 'err': 定義されていない識別子です。 1>c:\users\master\desktop\memo\memo\saver.cpp(33): error C3861: 'sqlite3_exec': 識別子が見つかりませんでした 1>c:\users\master\desktop\memo\memo\saver.cpp(37): error C2065: 'db': 定義されていない識別子です。 1>c:\users\master\desktop\memo\memo\saver.cpp(37): error C3861: 'sqlite3_close': 識別子が見つかりませんでした 1>c:\users\master\desktop\memo\memo\saver.cpp(40): error C2617: 'Saver': 'return' ステートメントが正しくありません。 1>c:\users\master\desktop\memo\memo\saver.cpp(6): note: 'Saver' の宣言を確認してください 1>memoDlg.cpp 1>コードを生成中... 1>スキップ中... (関連する変更は検出されませんでした) 1>memo.cpp 1>プロジェクト "memo.vcxproj" のビルドが終了しました -- 失敗。 ========== ビルド: 0 正常終了、1 失敗、0 更新不要、0 スキップ ==========
試したこと
saver.h
にsaver.cpp
の内容を書き、saver.cpp
内はコメントアウトした場合は想定通りに動きます。
saver.h
c++
1#pragma once 2 3#include "sqlite3.h" 4#include "stdafx.h" 5 6 7// sqlite3.dll内関数ポインタ型定義 8typedef int(__cdecl * pOpen)(char *, sqlite3 **); 9typedef int(__cdecl * pExec)(sqlite3 *, const char *, sqlite3_callback, void *, char **); 10typedef int(__cdecl * pGetTable)(sqlite3 *, const char *, char ***, int *, int *, char **); 11typedef int(__cdecl * pFreeTable)(char **); 12typedef int(__cdecl * pClose)(sqlite3 *); 13 14class Saver { 15 16 17 18public: 19 Saver(); 20 21 22public: 23 24 // 関数ポインタ変数 25 pOpen sqlite3_open; 26 pExec sqlite3_exec; 27 pGetTable sqlite3_get_table; 28 pFreeTable sqlite3_free_table; 29 pClose sqlite3_close; 30 31 32 HINSTANCE hDll; 33 sqlite3 *db; 34 char *err; 35 char **result; 36 int row, col; 37 CString str; 38}; 39 40Saver::Saver() { 41 42 AfxMessageBox(_T("saver constructed")); 43 // sqlite3.dllをロード 44 hDll = LoadLibrary("sqlite3"); 45 if (hDll == NULL) { 46 FreeLibrary(hDll); 47 AfxMessageBox(_T("dll cant be loaded.")); 48 return; 49 } 50 51 52 // sqlite3関数のアドレスを取得 53 sqlite3_open = (pOpen)GetProcAddress(hDll, "sqlite3_open"); 54 sqlite3_exec = (pExec)GetProcAddress(hDll, "sqlite3_exec"); 55 sqlite3_get_table = (pGetTable)GetProcAddress(hDll, "sqlite3_get_table"); 56 sqlite3_free_table = (pFreeTable)GetProcAddress(hDll, "sqlite3_free_table"); 57 sqlite3_close = (pClose)GetProcAddress(hDll, "sqlite3_close"); 58 59 60 61 // データベースファイルを作成 62 sqlite3_open("test.db", &db); 63 64 // テーブル作成 65 sqlite3_exec(db, "create table test(num integer,name string);", NULL, NULL, &err); 66 // データを格納 67 sqlite3_exec(db, "insert into test values(1,'test1');", NULL, NULL, &err); 68 69 70 // データベースファイルを閉じる 71 sqlite3_close(db); 72 73 74}
質問のMFCのコードではなぜ、クラスやそのメンバ変数を見つけられないのでしょうか?
よろしくお願い致します。
回答3件
あなたの回答
tips
プレビュー