static宣言を複数のソースファイルで共有したいと考え以下のようなプログラムになりました
やはりstaticの共有は無理でしょうか。
リソースファイルの記載内容
static HANDLE hInfoData;
関数と関数1は同じソースファイル
void関数(){
hInfoData = CreateFile(・・・)
}
void関数1(){
関数();
ここではhInfoDataが有効
}
別のソースファイル
リソースファイルをインクルード
void関数2(){
ここではhInfoDataがNULLになる
}
No.8ベストアンサー
- 回答日時:
source.c に
#include "header.h"
と書くと, これは
source.c の当該位置に header.h の内容を全部書く
のと基本的に同じ意味になります. つまり
static HANDLE hInfoData;
と書いてあるヘッダファイルを複数のソースで #include すると, それぞれのソースに
static HANDLE hInfoData;
と書いたのと同じ効果を発揮します.
そして, static な変数はその宣言のあるソースファイルの中でしか使えず, 複数のソースファイルで static と宣言するとそれぞれのソースファイルごとにその static な変数が作られます. もちろん, それらは「たまたま名前が同じ」であるだけで, 実体としては異なる変数となります.
それで、複数のソースに同名の変数名でstatic宣言してもエラーにならなかったのですね、但し、同名でも別物という訳ですか・・・
ヘッダーファイルに、スターティク宣言した変数を置くことはなんら問題ないことはわかりました、ただし、ご回答の意味は承知しておく必要はあるようです。
ありがとうございました。
No.12
- 回答日時:
>それにしても、変数の内容が自然に変わるのは何故でしょう、変わらなければstaticは必要ないわけですが・・・
>一般的な変数をstaticにしたとたん、バグが解決した事例も沢山あります。
まぁ、既にツッコミありますけど…現象確認できるコードを掲示してください。
可能性としては……
・ローカル変数(いわゆるauto変数)に値を設定、次にコールされた時に値が壊れているのはなじぇ?
(未初期化のローカル変数はそういうものです。)
・グローバル変数で値設定しているのにいつの間にか値変わっているのはなじぇ?
(おそらくバグでどこかから書き換えを行っています。ポインタや配列使っているならその辺り注意しましょう。)
>やはり、混乱を招くようです、今回はソース行が膨大になっても複数ソースを1ファイルにする方向で検討します。
たぶん、後で混乱するからやめておいた方がいいんですけどねぇ。
機能ごとなどでファイルは分割しておかないと見通し悪くなりますよ。
# で、グローバル変数が妙なところ(関数定義と関数定義の間とか)に書かれていて、見失うとか。
コードの提示したいですが、体系だてて取り上げる箇所が見当たらないので、ごめんなさい。
変数飛ぶのが怖いので、ソース一本化してstaticで頑張ります。
ありがとうございました。
No.11
- 回答日時:
「変数の内容が自然に変わる」というのはどういうことでしょうか? 例えば放射線の影響でメモリの内容が変わるなどの事例は知られていますが, 通常そのようなケースは除外して考えるので変数の値は「プログラムで変えない限り変わらない」とみなすはずです.
「変数の内容が自然に変わる」ような, 具体的かつ簡単なプログラムはありませんか?
申し訳ありませんが、何処から何処までが関係しているか判らないのです、提示する箇所が特定できないため、一般的なことしかお伝えできません。
何度も回答いただきありがとうございました。
No.10
- 回答日時:
大丈夫かなぁ....
文法上ヘッダファイルに static な宣言を書くことに何らの問題もありません. ただ, static な宣言を含むヘッダを書かなければならない現実的な理由もほとんどないはずです. つまり,
ヘッダファイルには static な宣言を書かない
を原則とすべきです.
Tacosanありがとうございます、
やはり、混乱を招くようです、今回はソース行が膨大になっても複数ソースを1ファイルにする方向で検討します。
他のソースにはコマンドラインで解決します。
ありがとうございました。
No.9
- 回答日時:
>ヘッダーファイルに、スターティク宣言した変数を置くことはなんら問題ないことはわかりました
メモリを無駄にしている。とか、
変更したつもりが別の変数だったので適用されていなかった。なじぇ?とかの問題に目をつぶれば…でしょうかね。
(不具合出た時に)面倒なんでそんな書き方しているプロジェクトメンバーが居たら、お説教ってところでしょうか。
# ルネサスマイコンで現在仕事していますが…RAMが64Kしかないのでやりくり必死ですわ。
# で、デバッガのウオッチでみられない。ということで、一時的にstatic変数にしている人は居ますけどね。
# 最適化でいろいろ変わるのでデバッグも結構大変…。
>変更したつもりが別の変数だったので適用されていなかった。なじぇ?とかの問題に目>をつぶれば…でしょうかね。
まさにこれが今回ぶち当たった原因かも知れません、いや全くこれが原因。
やはり、オーソドックスに書き上げるのが無難のようです。
それにしても、変数の内容が自然に変わるのは何故でしょう、変わらなければstaticは必要ないわけですが・・・
一般的な変数をstaticにしたとたん、バグが解決した事例も沢山あります。
No.7
- 回答日時:
No.5です。
>ご指摘のような直接な変更は私の記憶ではないのですが、
そりゃ、ないでしょう。
でも世の中には、
if (hInfoData == NULL) {
と書くつもりが
if (hInfoData = NULL) {
と書いてしまう人はいくらでもいます(恐らくほぼすべてのプログラマは経験しているでしょう)。
>ソース行数が大きくなっている分、時間をかけて確認する必要はあるようです。
この程度の話であれば、たとえソースファイルが100以上あろうとも、総コード行数が100万行あろうとも、ソースコードをテキスト検索すれば一発で分かります。
>まさか、コンパイラが壊れた・・・とか?
コードレビューするときに必ず言う言葉ですが、「プログラムは書いた通りにしか動かない」です。
プログラムに関しては、意図通りに動かない原因に外的要因はありませんので、まず外的要因を排除して調べてみてください。
なお、自分で作ったCPUで、そのCPUのために自前で作ったコンパイラにバグがあった、ということであればその限りではありません。
No.5
- 回答日時:
No.3です。
>プログラムで立ち上げ時に一度だけ初期設定した後は、書き込みはせず読み出すだけなのにです、不思議です!!
仮に、どこかにこんな風に書いてあるとしたら、全然不思議じゃないです。
if (hInfoData = NULL) {
...
}
これは、No.3で回答した
>いつの間にか空白に「している」
にあたります。
そんな初歩的なミスなどしていない、ということでしたら、ごめんなさい、本当にわかりません。
たびたびの回答ありがとうございます。
ご指摘のような直接な変更は私の記憶ではないのですが、ソース行数が大きくなっている分、時間をかけて確認する必要はあるようです。
まさか、コンパイラが壊れた・・・とか?
No.4
- 回答日時:
ファイルレベルのstaticは「共有しない」、つまり外部リンケージを作らず
コンパイル単位毎に別々にメモリを確保するぞ
という宣言なので、貴方のやりたいこととま逆です。
何故Cの作者が intern(internal) という修飾子にしなかったのか謎ですが・・・
何処かのソースでstaticをつけずに宣言。
他のソースからはexternで参照。
とするだけでグローバル変数を複数コンパイル単位で共有出来ます。
回答ありがとうございます。
この一般的な変数が行方不明になることはよく経験することで、プログラムが思うようにに動作しない点を、まさかこの行方不明が影響しているとは知らず毎日を無駄にした経験があります。
staticを宣言することで一発で解決した苦い経験があり。
何でも、staticにすることが身についております。
一般的な変数が行方不明になることは、まさかコンパイラやビルダーが壊れているのでしょうか?
お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!
似たような質問が見つかりました
- C言語・C++・C# c言語の問題です 3 2023/01/10 16:15
- C言語・C++・C# スタックフレームの消滅 6 2023/05/20 12:33
- Java javaでのプログラム(配列)について質問です. 2 2022/10/14 22:27
- Java java final 1 2022/06/10 22:49
- C言語・C++・C# const char** p;のとき、free(p)でC4090エラーとなるのはなぜですか 3 2023/03/31 16:28
- C言語・C++・C# C言語 ポインタ 配列 2 2022/06/02 17:29
- C言語・C++・C# c言語の問題です 課題1 (二分探索木とセット) 大きさ size の配列 array を考える。す 2 2023/01/10 21:08
- C言語・C++・C# 宣言する関数の形が決まっている状態で、 str1とstr2の文字列をこの順に引っ付けてstrに保存し 2 2022/05/30 18:21
- Java Java プログラム public class Main { public static void 3 2023/08/10 23:46
- C言語・C++・C# プログラム内から、MIDIファイルの一部分だけを再生する方法 1 2023/02/15 11:08
関連するカテゴリからQ&Aを探す
おすすめ情報
デイリーランキングこのカテゴリの人気デイリーQ&Aランキング
-
C#のクラスをVB.netで使用したい!
-
VB.NETでActiveX(OCXファイル)作成
-
VB.NETで他のプロジェクトで作...
-
VB6で、非表示モジュール(?)の...
-
ソースから参照しているOCXの一...
-
プリコンパイル?
-
libssh2のインクルード
-
コンパイルするときに、ファイ...
-
Visual Studioを使ったフォーム...
-
エラーの原因は?「この関数の...
-
Wingdi.h Windows.h を開くには?
-
同じソースコードなのにバイナ...
-
エントリポイントがDLLから...
-
C言語でのファイルの作成につい...
-
srand48? drand48?
-
ACCESSのEXEを作るのは可能...
-
VB6 exeファイルのプロパティの...
-
static宣言の共有
-
ユーザー名・作成者について(Vi...
-
「ソースファイルが見つかりま...
マンスリーランキングこのカテゴリの人気マンスリーQ&Aランキング
-
VB.NETで他のプロジェクトで作...
-
ACCESSのEXEを作るのは可能...
-
コンパイルするときに、ファイ...
-
C#のクラスをVB.netで使用したい!
-
エラーの原因は?「この関数の...
-
他の.CPPファイルに定義した関...
-
VB6で、非表示モジュール(?)の...
-
VC++でexeファイルが作成できま...
-
ソースから参照しているOCXの一...
-
Visual Studioでプロジェクトが...
-
VisualBasicを保存するときにで...
-
srand48? drand48?
-
「マージする」とは?
-
VB6 exeファイルのプロパティの...
-
プリコンパイル?
-
VC++ 2005 Intellisenseを更新....
-
libssh2のインクルード
-
Visual Studioを使ったフォーム...
-
同じソースコードなのにバイナ...
-
c言語として保存できない
おすすめ情報