【初心者歓迎】C/C++室 Ver.70【環境依存OK】
リンカの動作は規格で定めるものじゃないんだからわからんとしか…
気になるなら分けておけばいいじゃん
環境依存OKなスレだから、規格で決まっていないことを質問しても問題は無い
環境依存の質問がダメって言ったつもりはなかったんだが
まぁすまんかった
DLLが公開してる関数のようにEXEから関数を公開する事はできますか?
>>955 関数を公開することはできる。やり方はDLLの場合と同じ。
ただし、DLLとして読み込むのは難しいと思う。できる方法を自分は知らない。
>>952-954 申し訳ありませんでした。
規格によってリンク時の動作が決まっているものではない
ということを知らなかったのです。
ちなみに、VC6やVC2005やVC2008のリンカだと
使っていないものはリンク時に外してくれるものなのでしょうか?
「便利クラス&関数群」みたいなライブラリを作ろうかと思ったのですが。
だからobjファイルごとだって。
どこからも参照されてないobjはリンクされないが、一か所でも使われてるとobj全部リンクされる。
関連の無いものはそれぞれ別のc/c++ファイルにしておけばいいよ
補足しておくと、libはobjファイルを集めたもの。
1個の.Cファイルをコンパイルしてobjを作り、それをlibにしたら常に全部リンクされる。
関数一つ一つばらしておけば、使ってるやつだけリンクされる。
>>958-959 そういうことでしたか。
基本的にはクラスごとにソースは分けてあるので、
ライブラリ自体は1つにまとめてビルドしてしまっても、
アプリケーションが使っていないクラスは
リンク時に捨ててくれるということですね。
配列&文字列は、参照私できないの?
できるぞ
#include <iostream>
void foo(int (&a)[10]) {
a[0] = 42;
}
int main() {
int a[10];
foo(a);
std::cout << a[0] << std::endl;
}
要素数固定なのか、うむポインタにしよう
可変にできないこともない
#include <iostream>
template <int N>
void foo(int (&a)[N]) {
a[0] = 42;
};
int main() {
int a[10];
foo(a);
std::cout << a[0] << std::endl;
}
>>956 難しいですか
DLLにコールバック関数を持たせてアプリケーションを拡張できるように・・・というのをやろうとしてるんですが
そうなるとAPIを提供する仲介用DLLと拡張用DLLを両方用意しないと駄目みたいですね
レスどうもでした
>>965 アプリケーションを拡張できるように
アプリケーション側が
決まった関数名 を エクスポートする DLL を LoadLibaray で取り込む→GetProcAddress でDLL側の関数保持
状況に応じて その DLL 内関数を呼び出す
こういう構造を容易しておいて
拡張を記述する側は
アプリケーション側の呼び出しルールに応じた 関数を書けばOK
こういう造りが多いんじゃね?
>>965 EXE内で定義した関数を、関数へのポインタとしてDLL内の関数へ渡すのはできるよ。
難しいと書いたのはEXEファイルをLoadLibraryしたりLIBでリンクしたりということ。俺の勘違いだったらすまない。
横槍すまない。
>>964 すげー。以下のようなコードを書いたら通ってしまった。
スタティック配列始まったな。
template<class T,size_t N>
void Init(T (&Array)[N]){
T Val(0);
for(size_t i=0;i<N;i++){
Array[i] = Val;
}
}
969 :
933-940:2010/01/27(水) 18:35:14
先日は色々ご教授ありがとうございました。
色々調べまくった結果、
scanf("%[abcre12345]",&c);
この部分を
scanf("%c",&c);
こうすることで何とか解決することが出来ました。
ありがとうございました。
これで何とかなりそうです。
>>966,967
レスサンクスです
EXE側のオブジェクトを操作するのに操作用のAPIをDLLで提供しなければいけないかなと思ったんですが、なんとか拡張用DLLだけでできそうです
レスをまとめるとこんな感じですかね
//--Main側--
class Hoge
{
public:
Hoge(void) { /* DLLからHogeUpdateをロード */ }
void Update(void);
void SetX(int x) { m_x = x; }
int GetX(void) { return m_x; }
private:
int m_x;
void (*m_HogeUpdate)(void *handle, HogeFunc *hogeFunc); // コールバック用の関数ポインタ
};
//公開する関数
void HogeSetX(void *handle, int x) { ((Hoge *)handle)->SetX(x); }
int HogeGetX(void *handle) { return ((Hoge *)handle)->GetX(); }
struct HogeFunc { void (*SetX)(void *handle, int x); int (*GetX)(void *handle); };
//拡張用関数をコール
void Hoge::Update(void) { HogeFunc hogeFunc = { HogeSetX, HogeGetX }; m_HogeUpdate(this, &hogeFunc); }
//--DLL側--
//公開する関数
void HogeUpdate(void *handle, HogeFunc *hogeFunc) { /* 拡張によって異なる。handleとhogeFuncでオブジェクトを操作 */ }
リストのつなぎ換えがしたくてこういうコードを書いたのですが
std::listのsplice関数ってこんな感じで自分自身に使っても大丈夫なんでしょうか
↓2番目と3番目の要素を交換するプログラム
typedef list<int> LI;
LI l;
for(int i=0;i<4;++i){l.push_back(i);}
LI::iterator i1=++l.begin();
LI::iterator i2=++(++l.begin());
l.splice(i1,l,i2);
copy(l.begin(),l.end(),ostream_iterator<int>(cout," "));
>>959 あれ?リンカは賢くて必要にして十分なobjをリンクしてくれるものと思っていましたが、違いましたか。
>972
良く読め。
「1個の.Cファイルをコンパイルしてobjを作り、それをlibにしたら」
>>967 GetProcAddress(NULL, "func");
調べてみたところMSDNには書いてないけどこれでEXEから公開した関数にアクセスできるみたいですね
正しい使い方なのかわかりませんが・・・
自前のスタティックライブラリを作成したのですが
やはりnamespaceを宣言しておいた方がいいのでしょうか?
vector<class A> vec;で宣言したクラスAのメンバへのアクセスの仕方を教えてください
vec[0].member
>>978 まず、何らかのAをpush_backする。またはリサイズで確保する。
配列的なindexアクセスか、vectorのbackメンバで要素にアクセス。
ドット演算子でAのメンバにアクセス。
vec[0].A_Method();
vec.back().A_Method();
という流れじゃない?
981 :
980:2010/01/28(木) 23:48:46
おっと、被った。
>>979,980,981 さん
ありがとうございます.
>>976 NULLの代わりにGetModuleHandle(NULL)を使えば心配要らない。
>>977 それだけの情報じゃなんとも言えん。好きにしろ。
Handle foo(void)
{
static my::AutoPtr<Handle> resource(Load("resource-name"), Rereaser);
return resource.get();
}
これってアプリ終了時にちゃんと開放してくれますかね?
>>985 「ちゃんと開放」となるかどうかは知らないが、 resource のコンストラクタが成功すれば、
のデストラクタは main() 終了時や exit() 呼び出し時に呼び出されることになってる。
× rerease
○ release
× 開放
○ 解放
次スレ誰か頼む
そういえば昔
○開放
×解放
な現場があったな…占有してる「場所を開け放つ」んだから開放だとか…
えぇーって思ったけど
あの娘を解き放て!
あの娘は仮想メモリだぞ!
元ネタなに?
アシタカせっ記
ウメハラがぁ!!
捕まえてぇぇ!!!
ばーすとよんで
まだ入るぅぅ!!
ウメハラがぁっ!!!!・・・つっ近づいてぇっ!!!
ウメハラがぁ決めたぁぁーっ!!!!
1001 :
1001:
このスレッドは1000を超えました。
もう書けないので、新しいスレッドを立ててくださいです。。。