クラス内関数に宣言したStatic変数について
class A
{
public func()
{ static int i = 0;
i++;
TRACE( i=%d\n, i);
};
}
のとき
A a1, a2, a3;
a1.finc(); -> i=1
a1.finc(); -> i=2
a2.func(); -> i=3
a2.func(); -> i=4
a3.func(); -> i=5
a3.func(); -> i=6
となりますが、
a1.finc(); -> i=1
a1.finc(); -> i=2
a2.func(); -> i=1
a2.func(); -> i=2
a3.func(); -> i=1
a3.func(); -> i=2
としたい場合は、iをclass Aのstaticでないメンバー変数に
しなければいけないのでしょうか?
func()内で、インスタンス毎にローカルな静的変数(static)の定義は
できないのでしょうか?
> func()内で、インスタンス毎にローカルな静的変数(static)の定義は
> できないのでしょうか?
メンバ関数のfunc内で、インスタンス毎にローカルなstatic変数とい
うのは無理ですが、TKHさんがされたいことはデータメンバを使うことで
実現できるのではないかと…。
データメンバならインスタンスが存在している間は存在していますので、
func関数ではまるでスタティックな変数にアクセスしているかのように扱
えると思います…。はずしてたらごめんなさい。
> func()内で、インスタンス毎にローカルな静的変数(static)の定義は
> できないのでしょうか?
インスタンス毎にローカルで静的な変数とは、
どのような性質を持つ変数だとお考えですか?
メンバ変数ではなにか問題がありますか?
ありがとうございます。
>TKHさんがされたいことはデータメンバを使うことで
>実現できるのではないかと…。
確かにデータメンバにすればできます。
説明不足でした。
少し詳しく説明します。
過去のCで書かれた下記のソースコードを利用したいとき、
void func()
{
static int OldData = 0;
int NewData = GetData(); //現在のデータ値を取得
if( OldData != NewData){
・・・・・
}
OldData = NewData;
}
(このような過去のCのソースコードが沢山あるのです)
ソースコードをコピーペーストでもってくるのですが、
この中の「static int OldData = 0;」宣言を
クラスメンバーに変更し、さらにコンストラクターで初期化
するという修正が必要になってしまったので
何かほかにやり方があるのかと思い質問しました。
> この中の「static int OldData = 0;」宣言を
> クラスメンバーに変更し、さらにコンストラクターで初期化
> するという修正が必要になってしまったので
> 何かほかにやり方があるのかと思い質問しました。
CからC++への移行ということで、特に今回のようにクラス化するのであれば、
設計を見直してかなり慎重に組まないと後で泣きを見そうな気配です。(^^;
単純なコピー&ペーストによる実作業だけではなく、ある程度想定される今回の
ようなパターンを一通り洗い出してから、まとめて直される方が良いような気がし
ます。現時点で既にその作業を終えているとすると、まだ足りないのかも…。
ひょっとしてさん dairygoodsさん
ありがとうございました。
クラスのメンバー変数にする方向です。
<愚痴なのですが>
ただ、メンバー関数のfunc()内でローカルに使う1ワーク変数を
クラスのメンバー変数にしなくてはならず、クラスグローバルな変数に
なるというのが、少し腑に落ちない部分です。
> ただ、メンバー関数のfunc()内でローカルに使う1ワーク変数を
> クラスのメンバー変数にしなくてはならず、クラスグローバルな変数に
> なるというのが、少し腑に落ちない部分です。
それは、オブジェクトの切り分けがうまくいっていないということです。
そのような場合、メンバー関数func()とワーク変数を
組み合わせた新しいクラスを作ります。
> ただ、メンバー関数のfunc()内でローカルに使う1ワーク変数を
> クラスのメンバー変数にしなくてはならず、クラスグローバルな変数に
> なるというのが、少し腑に落ちない部分です。
使い終わったら自動的に消え失せるんだからいいじゃない。
むしろ static にすることで使おうが使うまいがそこに
居座りつづける方がよっぽど腑に落ちない。
> ただ、メンバー関数のfunc()内でローカルに使う1ワーク変数を
> クラスのメンバー変数にしなくてはならず、クラスグローバルな変数に
> なるというのが、少し腑に落ちない部分です。
そうですね。確かに他のメンバ関数には関係のない(と思われる)変数ですし、
他のメンバ関数にアクセスされてしまう可能性があるというのも、なんだか腑に
落ちないかもしれません。(^^;
ただ、もともとのプログラムの中でstaticとして使われていた理由を考えれば
納得のいく形に納めることも可能かもしれませんね。
例えば、「前回処理されたときの結果と今回の処理結果を比較したい」という
ような場合に、関数内部でstaticにした変数を使っている場合が多そうなので、
その辺の処理がクラス化するときに最適な状態に出来れば良いのではないかと…。
参考意見ありがとうございました。