Копирует ли это ссылку или объект? - PullRequest
1 голос
/ 16 июня 2010

Извините, я толстый и ленивый, но в основном ленивый. На самом деле, даже не это. Я пытаюсь сэкономить время, чтобы я мог делать больше за меньшее время, так как многое еще предстоит сделать.

Копирует ли это ссылку или фактические данные объекта?

public class Foo
{
    private NameValueCollection _nvc = null;

    public Foo( NameValueCollection nvc)
    {
        _nvc = nvc;
    }
}

public class Bar
{
    public static void Main()
    {
        NameValueCollection toPass = new NameValueCollection();
        new Foo( toPass ); // I believe this only copies the reference
                           // so if I ever wanted to compare toPass and 
                           // Foo._nvc (assuming I got hold of the private 
                           // field using reflection), I would only have to
                           // compare the references and wouldn't have to compare
                           // each string (deep copy compare), right?
}

Я думаю, что знаю ответ наверняка: он только копирует ссылку. Но я даже не уверен, почему я спрашиваю об этом.

Полагаю, меня беспокоит только то, что после создания экземпляра Foo путем вызова его параметризованного ctor с toPass, если мне нужно убедиться, что NVC я передал как toPass, а личное поле NVC _nvc имел точно такой же контент, мне просто нужно было бы сравнить их ссылки, верно?

Ответы [ 4 ]

3 голосов
/ 16 июня 2010

Да, это правильно.Однако, если вы хотите сравнить toPass и Foo._nvc позже, вы все равно можете захотеть сделать сравнение по элементам, чтобы такие разные, но эквивалентные коллекции сравнивали равные.

1 голос
/ 16 июня 2010

Одним словом, да.

0 голосов
/ 16 июня 2010

Вы передаете ссылочный тип по значению. Вы можете изменить данные, на которые указывает ссылка (например, добавить новые элементы в коллекцию), и изменения будут отражены для вызывающей стороны. Как указал Мэтью, вам все еще может потребоваться проверить наличие различных, но еще не эквивалентных объектов.

При условии, что вы придерживаетесь напечатанного вами использования и не выполняете никаких "новых" операций, ссылки на объекты останутся эквивалентными.

public class Foo 
    { 
        public NameValueCollection _nvc = null;

        public Foo( NameValueCollection nvc) 
        {
            //this is cool
            _nvc = nvc;
            _nvc.Add("updated", "content");

            //this isn't cool. Now you have a new object with equivalent members and you should follow Matthew's advice
            //_nvc = new NameValueCollection();
            //_nvc.Add("foo", "bar");
            //_nvc.Add("updated", "content");
        } 
    }

    public class Bar
    {
        public static void Main()
        {
            NameValueCollection toPass = new NameValueCollection();
            toPass.Add("foo", "bar");
            Foo f = new Foo(toPass); 

            if (Object.Equals(toPass, f._nvc))
                Console.WriteLine("true");
            else
                Console.WriteLine("false");
            Console.ReadLine();
        }
    }
0 голосов
/ 16 июня 2010

Редактировать: Да, это скопировало значение ссылки.

Я также согласен с Мэтью Флашеном в отношении глубокого сравнения копий, а также перегрузки вашего оператора сравнения равенств

...