2013-08-24 5 views
1

Что делать, если мне нужен одноразовый элемент для всего запуска моего приложения? Есть некоторые случаи, когда это кажется необходимым, например, если я хочу синхронизировать 2 потока с: System.Collections.Concurrent.BlockingCollection.Что делать, если мне нужен одноразовый элемент?

Если один из потоков использует использование и распоряжается им, а другой Thread не смог завершить работу или ждать на BlockingCollection (вы можете установить тайм-аут), он затем получит Disposed Exception.

И, вероятно, есть больше случаев, когда это правда, так есть способ обойти это, или я должен просто сделать объект инициализацией и избавиться от него при закрытии?

EDIT: Вот что рассказывает Visual Studio, когда я использую одноразовый элемент.

Во-первых, как я использую его в качестве примера:

private void Initialize() 
     { 
      Queue = new System.Collections.Concurrent.BlockingCollection<byte[]>(); 
      Queue.Dispose(); 
     } 

И я получаю это:

warning : CA2213 : Microsoft.Usage : 'Capture' contains field 'Capture.Queue' that is of IDisposable type: 'BlockingCollection<byte[]>'. Change the Dispose method on 'Capture' to call Dispose or Close on this field. 

Так что просто get's меня путают. Я сказал это, чтобы избавиться сразу после это было сделано, и он все еще хочет, чтобы я, чтобы избавиться от него: S

EDIT 2:

Является ли это правильный способ утилизации объекта, которые должны быть в живых запущено все приложение?

protected override void Dispose(bool disposing) 
{ 
    if (disposing && (components != null)) 
    { 
     components.Dispose(); 
     Queue.Dispose(); 
    } 
    base.Dispose(disposing); 
} 

Как вы можете видеть, я добавил туда очередь.

Это не кажется правильным, хотя, кажется странным работать с файлом Designer.cs и добавлять материал по компонентам. Dispose();

Но, надеюсь, это правильно.

+1

Не используйте использование на объекте и инициализируйте его при запуске программы, а утилита при закрытии программы. Проблема, которую вы не можете гарантировать кому-то другому, не будет использовать 'использование' на объекте? – crush

+0

Проблема в том, должен ли я это сделать? Visual Studio ненавидит, когда я не использую «Использование», он говорит (вам нужно распоряжаться одноразовыми объектами), даже если я скажу ему, чтобы он удалял объект в Close. Так что это просто меня смущает – Zerowalker

+0

Почему вы его немедленно уничтожаете в блоке 'Initialize()'? Это просто проверить тестовые сообщения в VS? – crush

ответ

3

Шаблон формы проекта формы вызывает проблемы программистов. Они знают, что вы не должны редактировать файл Designer.cs. Но это не так прямолинейно. Откройте файл и отметьте область:

#region Windows Form Designer generated code 

Это код, который вы не должны связываться. И обратите внимание, что ограничение Disposing (bool) - выше в этом регионе. Это означает, что это просто прекрасно, чтобы изменить это.

Лучше всего просто вырезать/вставить метод Dispose() из файла Designer.cs в файл исходного кода формы.Теперь у вас нет проблем, следуя советам аналитика:

protected override void Dispose(bool disposing) { 
     if (disposing) Queue.Dispose(); 
     if (disposing && (components != null)) { 
      components.Dispose(); 
     } 
     base.Dispose(disposing); 
    } 
+0

Спасибо, это тот же ответ, что и другие, но он объясняет немного больше :) – Zerowalker

+0

Каковы преимущества или недостатки этого, а также наличие формы подписаться на собственный метод FormClosed или Disposed? – supercat

1

Просто потому, что объект является одноразовым, не означает, что вы должны его уничтожить! Не используйте блок using: это будет уничтожать объект после его выхода из области видимости. Просто создайте экземпляр объекта в обычном режиме и утилизируйте его в удобное для вас время (или никогда, если вы планируете использовать его на протяжении всего срока службы приложения).

+0

А хорошо, что приятно слышать :) Хотя, чтобы создать он в начале, где я должен это делать, поскольку есть много мест, я должен это сделать, FormLoad, при инициализации или при запуске в Private myDisposableobject object = new myDisposableobject(); ? – Zerowalker

+0

Где хранится основная ссылка на одноразовый объект? – crush

+0

Ссылка находится вверху, как приватная переменная в классе. – Zerowalker

1

Visual Studio предупреждает вас, что ваш объект (форма под названием Capture) имеет одноразовое поле. Он говорит, что, когда вы удаляете форму, вы также должны уничтожить BlockingCollection. Это верно. Он не может узнать, будет ли ваше приложение продолжено после того, как форма будет удалена, поэтому вам нужно очистить форму и ее одноразовые поля, когда вы закончите с ней.

+0

Но как мне «очистить» его ?. Я удаляю объект, и он до сих пор «не получил». Что-то не так с тем, как я это делаю? – Zerowalker

+0

Не удаляйте объект прямо там, где он был создан (он перестанет быть полезным почти сразу). Вместо этого удалите объект в методе 'Dispose' формы (добавьте его, если его еще нет). – CSJ

+0

Так что мне нужно поместить его в код Designer.cs? потому что я предполагаю, что это метод Dispose из того, что я вижу. – Zerowalker