Почему клонируется (в.NET) настолько трудный?

Похож на Вас, пытаются защитить от медленная распределенная грубая сила . Не то, чтобы очень можно делать с этим. Мы используем PKI и никакие логины пароля. Помогает, но если Ваши клиентские рабочие станции шанса время от времени, это не очень применимо.

20
задан juan 20 August 2009 в 21:04
поделиться

5 ответов

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

Если вы хотите реализовать именно эту функциональность, это просто - это для чего предназначен Object.MemberwiseClone () . Большую часть времени,

24
ответ дан 30 November 2019 в 00:01
поделиться

Другие уже рассказали о MemberwiseClone , но никто не объяснил , почему он защищен. Я попытаюсь дать объяснение.

Проблема в том, что MemberwiseClone просто слепо копирует состояние. Во многих случаях это нежелательно. Например, объект может иметь частное поле, которое является ссылкой на список List . Неглубокая копия, такая как то, что делает MemberwiseClone , приведет к появлению нового объекта, указывающего на тот же список - и класс вполне может быть написан, не ожидая, что список будет передан кому-либо еще.

Или объект может иметь какое-то поле идентификатора, сгенерированное в конструкторе - опять же, когда вы его клонируете, вы получаете два объекта с одинаковым идентификатором, что может привести ко всевозможным странным сбоям в методах, предполагающих, что идентификатор уникален.

Или скажем, у вас есть объект, который открывает сокет или файловый поток и сохраняет ссылку на него. MemberwiseClone просто скопирует ссылку - и вы можете представить, что два объекта, пытающиеся перемежать вызовы одного и того же потока, не закончатся хорошо.

Короче говоря, «клонирование» - это не лучший вариант. определенная операция для произвольных объектов. Тот факт, что элементарный operator = предоставляется для всех классов по умолчанию в C ++, является большим неудобством, так как слишком часто люди забывают, что он есть, и не отключают его для классов, для которых копирование не имеют смысл или опасны (а таких классов на удивление много).

Или, скажем, у вас есть объект, который открывает сокет или файловый поток и хранит ссылку на него. MemberwiseClone просто скопирует ссылку - и вы можете представить, что два объекта, пытающиеся перемежать вызовы одного и того же потока, не закончатся хорошо.

Короче говоря, «клонирование» - это не лучший вариант. определенная операция для произвольных объектов. Тот факт, что элементарный operator = предоставляется для всех классов по умолчанию в C ++, является большим неудобством, так как слишком часто люди забывают, что он есть, и не отключают его для классов, для которых копирование не имеют смысл или опасны (а таких классов на удивление много).

Или, скажем, у вас есть объект, который открывает сокет или файловый поток и хранит ссылку на него. MemberwiseClone просто скопирует ссылку - и вы можете представить, что два объекта, пытающиеся перемежать вызовы одного и того же потока, не закончатся хорошо.

Короче говоря, «клонирование» - это не лучший вариант. определенная операция для произвольных объектов. Тот факт, что элементарный operator = предоставляется для всех классов по умолчанию в C ++, является большим неудобством, так как слишком часто люди забывают, что он есть, и не отключают его для классов, для которых копирование не имеют смысл или опасны (а таких классов на удивление много).

MemberwiseClone просто скопирует ссылку - и вы можете представить, что два объекта, пытающиеся перемежать вызовы одного и того же потока, не закончатся хорошо.

Короче говоря, «клонирование» - это не лучший вариант. определенная операция для произвольных объектов. Тот факт, что элементарный operator = предоставляется для всех классов по умолчанию в C ++, является большим неудобством, так как слишком часто люди забывают, что он есть, и не отключают его для классов, для которых копирование не имеют смысл или опасны (а таких классов на удивление много).

MemberwiseClone просто скопирует ссылку - и вы можете представить, что два объекта, пытающиеся перемежать вызовы одного и того же потока, не закончатся хорошо.

Короче говоря, «клонирование» - это не лучший вариант. определенная операция для произвольных объектов. Тот факт, что элементарный operator = предоставляется для всех классов по умолчанию в C ++, является большим неудобством, так как слишком часто люди забывают, что он есть, и не отключают его для классов, для которых копирование не имеют смысл или опасны (а таких классов на удивление много).

8
ответ дан 30 November 2019 в 00:01
поделиться

Существует (по крайней мере) два вида клонирования. В большинстве источников говорится о мелком и глубоком клонировании, но на самом деле между ними есть оттенки.

Ключевая проблема - это противоречие между тем, «сколько следует скопировать» и «сколько» должны быть общими ".

Рассмотрим объект Order , содержащий ссылки на клиента , адрес и список List из OrderLines .

Если вы хотите Clone () an Order , в чем дело?

" Просто копирование блока памяти "даст вам новый Заказ , но тот, который разделяет Клиента , Адрес и тот же Список из OrderLines . (Помните, что члены объекта хранятся по ссылке, поэтому, когда вы дублируете блок памяти, вы получаете две ссылки на один и тот же объект.)

Очевидно, вы не хотите делиться списком of OrderLines между двумя Order s. Фактически, вы, вероятно, захотите также клонировать каждую OrderLine .

Если бы вы работали с методом общего назначения Clone () , как бы этот метод узнал, какие члены должны быть рекурсивно клонированы, а какие нет?

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

И последнее замечание: даже когда я создаю возможность Clone () объектов, я не склонен создавать метод Clone () , вместо этого предпочитаю конструктор копирования - конструктор, принимающий за основу другой объект. Если вы не можете найти Clone () , поищите его.

4
ответ дан 30 November 2019 в 00:01
поделиться

Вы должны явно реализовать интерфейс ICloneable в своих классах.

Однако, как указано в документации, механизм клонирования в MemberwiseClone делает не различать мелкую и глубокую копию.

0
ответ дан 30 November 2019 в 00:01
поделиться

Существует такая вещь, как Object.MemberwiseClone (), , которая выполняет то, что вы описываете. Он делает неглубокую копию объекта.

Он не будет выполнять глубокое клонирование автоматически ... вам нужно будет вызвать clone для всех объектов-членов вручную и т. Д.

2
ответ дан 30 November 2019 в 00:01
поделиться
Другие вопросы по тегам:

Похожие вопросы: