Подтвердить что ты не робот

Передача типов ссылок по значению в С#

Я хочу передать ссылочный тип по значению методу в С#. Есть ли способ сделать это.

В С++ я всегда мог полагаться на конструктор копирования, чтобы вступить в игру, если бы я хотел передать значение Value. Есть ли способ в С#, кроме: 1. Явное создание нового объекта 2. Реализация IClonable, а затем вызов метода Clone.

Вот небольшой пример:

Возьмем класс A в С++, который реализует конструктор копирования.

Метод func1 (класс a), я могу назвать его, сказав func1 (objA) (автоматически создает копию)

Есть ли что-то подобное в С#. Кстати, я использую Visual Studio 2005.

4b9b3361

Ответ 1

Нет, в С# нет эквивалента конструктора-копии. То, что вы проходите (по значению), является ссылкой.

ICloneable также опасен, так как он плохо определен, является ли он глубоким или мелким (плюс он не очень хорошо поддерживается). Другой вариант - использовать сериализацию, но опять же, которая может быстро нарисовать гораздо больше данных, чем вы планировали.

Если проблема заключается в том, что вы не хотите, чтобы метод внесения изменений, вы можете подумать о том, чтобы сделать класс неизменным. Тогда никто не может сделать ничего противного.

Ответ 2

Как уже объяснялось, нет эквивалента конструкторам копии С++.

Другой метод - использовать конструкцию, где объекты неизменяемы. Для неизменяемых объектов нет (семантической) разницы между передачей ссылки и копией. Так разработан System.String. Другие системы (особенно функциональные языки) применяют эту технику намного больше.

Ответ 4

Согласно этой ссылке (уже опубликовано): http://msdn.microsoft.com/en-us/library/s6938f28(VS.80).aspx

Передача ссылочного типа по значению показана ниже. Тип ссылки arr передается по значению методу Change.

Любые изменения будут влиять на исходный элемент, если для массива не назначена новая ячейка памяти, в этом случае изменение полностью локально для этого метода.

class PassingRefByVal 
{
    static void Change(int[] pArray)
    {
        pArray[0] = 888;  // This change affects the original element.
        pArray = new int[5] {-3, -1, -2, -3, -4};   // This change is local.
        System.Console.WriteLine("Inside the method, the first element is: {0}", pArray[0]);
    }

    static void Main() 
    {
        int[] arr = {1, 4, 5};
        System.Console.WriteLine("Inside Main, before calling the method, the first element is: {0}", arr [0]);

        Change(arr);
        System.Console.WriteLine("Inside Main, after calling the method, the first element is: {0}", arr [0]);
    }
}

В заключение, для более подробного обсуждения, см. пост Джона Скита в этом вопросе:

Передача объектов по ссылке или значению на С#

Ответ 5

взгляните на this

public class Product
{
   public string Name;
   public string Color;
   public string Category;

   public Product(Product o)
   {
      this.Name=o.Name;
      this.Color=o.Color;
      this.Category=o.Category;
   } 
   // Note we need to give a default constructor when override it

   public Product()
   {
   }
} 
public Product Produce(Product sample)
{
   Product p=new Product(sample);
   p.Category="Finished Product";
   return p;
}
Product sample=new Product();
sample.Name="Toy";
sample.Color="Red";
sample.Category="Sample Product";
Product p=Produce(sample);
Console.WriteLine(String.Format("Product: Name={0}, Color={1}, Category={2}", p.Name, p.Color, p.Category));
Console.WriteLine(String.Format("Sample: Name={0}, Color={1}, Category={2}", sample.Name, sample.Color, sample.Category));