2

Tupleor型のようなKeyValuePair型と、その値を設定するオプション (可変型) が必要です。これらのニーズを満たす既存のジェネリックのアイデアはありますか?

(辞書は、私の目的にはある種のやり過ぎのようです)

KeyValuePair独自のクラスを作成することもできますが、変更可能な型が既に実装されていることを望んでいました。

4

3 に答える 3

2

ミュータブルを持つことの問題は、ある場所で値を変更すると、同じタプルを何度も参照してしまい、予期しない他の場所でも変更される可能性があることです。そのため、変更可能なチューブルを使用する場合、たとえばコレクションに入れる場合など、適切な場所でタプルを複製することについて非常に厳密にする必要があります。

しかし、変更可能なタプルは次のようになります。

public class MutableTuple<T1, T2> {
    public T1 Item1 { get; set; }
    public T2 Item2 { get; set; }

    public MutableTuple(T1 item1, T2 item2) {
        Item1 = item1;
        Item2 = item2;
    }
}
于 2013-08-17T11:54:47.287 に答える
1
public class MutableKeyValuePair<TKey, TValue>
{
    public TKey Key { get; set; }
    public TValue Value { get; set; }
}

それでおしまい。

于 2013-08-17T11:50:33.040 に答える
0

いいえ、ありません。あなたが1つであると考えない限りobject[]:-)

a の実装MutableTuple<T1, ...>は非常に簡単であることに注意してください。

a の完全な実装、 aMutableTuple<T1, T2, T3>とほぼ同等Tuple<T1, T2, T3>(さまざまなインターフェイスが公開されており、非公開では実装されていません) (部分的に の Mono 実装に基づいていますTuple<>)

public static class MutableTuple
{
    public static MutableTuple<T1, T2, T3> Create<T1, T2, T3>(T1 item1, T2 item2, T3 item3)
    {
        return new MutableTuple<T1, T2, T3>(item1, item2, item3);
    }
}

[Serializable]
public class MutableTuple<T1, T2, T3> : IComparable, IStructuralEquatable, IStructuralComparable
{
    public T1 Item1 { get; set; }
    public T2 Item2 { get; set; }
    public T3 Item3 { get; set; }

    public MutableTuple(T1 item1, T2 item2, T3 item3)
    {
        this.Item1 = item1;
        this.Item2 = item2;
        this.Item3 = item3;
    }

    public override bool Equals(object obj)
    {
        return this.Equals(obj, EqualityComparer<object>.Default);
    }

    public override int GetHashCode()
    {
        return this.GetHashCode(EqualityComparer<object>.Default);
    }

    public override string ToString()
    {
        var sb = new StringBuilder();

        sb.Append(this.Item1);
        sb.Append(", ");
        sb.Append(this.Item2);
        sb.Append(", ");
        sb.Append(this.Item3);
        sb.Append(")");

        return sb.ToString();
    }

    public int CompareTo(object obj)
    {
        return this.CompareTo(obj, Comparer<object>.Default);
    }

    public bool Equals(object obj, IEqualityComparer comparer)
    {
        if (obj == null)
        {
            return false;
        }

        var tuple = obj as MutableTuple<T1, T2, T3>;
        return tuple != null && (comparer.Equals(this.Item1, tuple.Item1) && comparer.Equals(this.Item2, tuple.Item2)) && comparer.Equals(this.Item3, tuple.Item3);
    }

    public int GetHashCode(IEqualityComparer comparer)
    {
        unchecked
        {
            int hash = 17;

            hash = (hash * 23) + comparer.GetHashCode(this.Item1);
            hash = (hash * 23) + comparer.GetHashCode(this.Item2);
            hash = (hash * 23) + comparer.GetHashCode(this.Item3);

            return hash;
        }
    }

    public int CompareTo(object obj, IComparer comparer)
    {
        if (obj == null)
        {
            return 1;
        }

        var other = obj as MutableTuple<T1, T2, T3>;

        if (other == null)
        {
            throw new ArgumentException();
        }

        int res = comparer.Compare(this.Item1, other.Item1);

        if (res != 0)
        {
            return res;
        }

        res = comparer.Compare(this.Item2, other.Item2);

        if (res != 0)
        {
            return res;
        }

        res = comparer.Compare(this.Item3, other.Item3);

        return res;
    }
}
于 2013-08-17T11:48:34.483 に答える