2008-11-05 3 views
21

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

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

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

Давайте возьмем класс А в C++, который реализует конструктор копирования.

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

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

ответ

8

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

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

19

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

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

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

0

взглянуть на 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)); 
1

По этой ссылке (уже размещен): http://msdn.microsoft.com/en-us/library/s6938f28(VS.80).aspx

Passing ссылочный тип по значению показан ниже. Тип ссылки 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]); 
    } 
} 

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

Passing Objects By Reference or Value in C#

Смежные вопросы