0

私がやろうとしているのは、変数への参照の配列を持つことです。これは、int へのポインターの C 配列に相当することを意味します (たとえば)。

例: (!!実際のコードではありません!!)

int a = 4;
int b = 5;
int c = 6;
List<ref int> tmp = new List<ref int>();

tmp.Add(ref a);
tmp.Add(ref b);
tmp.Add(ref c);

tmp[0] = 16;
tmp[1] = 3;
tmp[2] = 1000;

Console.Writeline(tmp[0] + " " + a); // 16 16
Console.Writeline(tmp[1] + " " + b); // 3 3
Console.Writeline(tmp[2] + " " + c); // 1000 1000

私の場合の詳細: 辞書のキーに対応する文字列のリストがあります。私が欲しいと思うのは、Type1 が int または string への参照であり、Type2 が Textbox への参照であるタプルのリストです。

このリストを反復処理し、文字列を使用して辞書から値を取得し (そしてそのデータを処理して)、その結果を Type1 に格納します。最終的には、これらの Type1 変数参照からデータを取得し、それらのデータを対応する Type2 Textbox にコピーします。

それが私がやりたいと思っていることの要点です。私のアプローチが過度に複雑であると誰かが考えている場合、悲しいことにテキストボックスをそのままにしておく必要があると言うでしょう。また、Type1 変数も別々にしておくことが望ましいですが、それほど必要ではありません。

さて、読んでみると、 Func<> は私が望むものに最も役立つように見えると思ったので、次を使用しようとしました(Type1では、intと文字列の両方を処理する必要があるため、オブジェクトとして)

List<Tuple<string, Func<object>, Func<object>>>

しかし、それを使用して変数への参照を取得する方法がわかりませんでした。

4

4 に答える 4

1

C# を使用して参照を保存することはできません。refメソッドを呼び出すときにのみキーワードを使用できます。

ポインターを使用できますが、fixed式とunsafeコンテキスト内でのみ使用できます。

デリゲートを使用してこの種のものを偽造することは可能ですが、それがあなたが探しているものかどうかはわかりません. また、アプローチを本当に再設計する必要があることもかなり確信していますが、それにもかかわらず、それを偽造する方法の例を次に示します...

まず、「値ラッパー」クラスを次のように記述します。

public class ValueWrapper<T>
{
    readonly Func<T>   get;
    readonly Action<T> set;

    public ValueWrapper(Func<T> get, Action<T> set)
    {
        this.get = get;
        this.set = set;
    }

    public T Value
    {
        get
        {
            return get();
        }

        set
        {
            set(value);
        }
    }
}

次に、それを使用して値を変更できます。

void run()
{
    int x = 0;

    var intWrapper = new ValueWrapper<int>(() => x, value => x = value);

    test(intWrapper);

    Console.WriteLine(x);  // Prints 42, which shows that x was changed.

    TextBox textBox = new TextBox {Text = ""};

    var stringWrapper = new ValueWrapper<string>(() => textBox.Text, value => textBox.Text = value);

    test(stringWrapper);

    Console.WriteLine(textBox.Text); // Prints "Changed".
}

static void test(ValueWrapper<int> wrapper)
{
    wrapper.Value = 42;
}

static void test(ValueWrapper<string> wrapper)
{
    wrapper.Value = "Changed";
}

次のように、あるメソッドでラッパーを作成し、ラッパーを使用して元のラップされたオブジェクトのプロパティを変更する別のメソッドに渡すこともできます。

void run()
{
    TextBox textBox = new TextBox {Text = ""};

    var wrapper = test1(textBox);
    test2(wrapper);
    Console.WriteLine(textBox.Text); // Prints "Changed"
}

void test2(ValueWrapper<string> wrapper)
{
    wrapper.Value = "Changed";
}

ValueWrapper<string> test1(TextBox textBox)
{
    return new ValueWrapper<string>(() => textBox.Text, value => textBox.Text = value);
}

警告: これはかなり頭を悩ませるコードにつながります。次に例を示します。

void run()
{
    var intWrapper = test();
    intWrapper.Value = 42;
    Console.WriteLine(intWrapper.Value); // Works, but where is the value? It can't be the x inside test()!
}

ValueWrapper<int> test()
{
    int x = 0;
    var intWrapper = new ValueWrapper<int>(() => x, value => x = value);
    return intWrapper;
}

そのため、test() 内から明らかにローカル変数をラップしているValueWrapperfromを返しました。test()そして、明らかに値を変更して出力できます...

もちろん、これは実際に起こっていることではありませんが、かなり混乱する可能性があります。

于 2013-06-19T12:41:14.583 に答える
0

私はこれを使用し、完璧に動作します:

指数

public int value1 = 3;
public int value2 = 4;
public int value3 = 5;

public void Method1()
{
    int[] values = { value1, value2, value3};
    for (int i = 0; i < values.Length; i ++)
    {
        Console.WriteLine(values[i]);
    }
}
于 2018-08-09T02:33:18.663 に答える