потоки еще не освоены .. все еще с ошибками ioexception - PullRequest
1 голос
/ 13 февраля 2011

Я создал несколько фоновых потоков для разбора XML-файлов и воссоздания новых XML-файлов.Теперь проблема, с которой я сталкиваюсь, заключается в том, что, хотя я использую синхронизацию с глобальными переменными, я все равно иногда получаю ошибки, и я уверен, что это всего лишь грубый способ кодирования, который я делаю, но мне было интересно, если кто-то лучшевариант.программный поток =

  • доступ к локальной папке и загрузка всех файлов в список
  • раздевание каждого файла в записи xml и помещение этих записей в массив
  • для анализа конкретных значенийи введите эти значения в таблицу базы данных
  • , теперь создайте поток и возьмите массив записей, и поток проанализирует
  • , проанализирует поток и создаст новый XML-файл
  • mainпоток продолжает с другой функцией, а затем идет и получает файл из списка.

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

    For Each g In resultsList
        gXmlList.Add(g)
    Next

    Dim bgw As New BackgroundWorker
    bgw.WorkerSupportsCancellation = True
    AddHandler bgw.DoWork, New DoWorkEventHandler(AddressOf createXML)
    AddHandler bgw.RunWorkerCompleted, AddressOf WorkComplete
    threadlist.Add(bgw)
    bgw.RunWorkerAsync()

  Private Sub createXML()
     num += 1
     Dim file As String = Module1.infile
     xmlfile = directoryPath & "\New" & dateTime.Now.ToUniversalTime.ToString("yyyyMMddhhmmss") & endExtension
     Thread.Sleep(2000)
     Dim doc As XmlDocument = New XmlDocument
     **xwriter = New XmlTextWriter(xmlfile, Encoding.UTF8)** this is where ioexception error
     xwriter.Formatting = Formatting.Indented
     xwriter.Indentation = 2
     xwriter.WriteStartDocument(True)
     xwriter.WriteStartElement("Posts")

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

    Dim j As Integer = 0

Ответы [ 2 ]

1 голос
/ 13 февраля 2011

Что ж, если у вас возникли проблемы с блокировкой потоков, вы можете просто обернуть свои действия в следующем поместье.

    'This will need to be out of scope so that all threads have access to it
    Dim readerWriterLock As New Threading.ReaderWriterLockSlim


    readerWriterLock.EnterWriteLock()
    xwriter = New XmlTextWriter(xmlfile, Encoding.UTF8)
    'other logic
    readerWriterLock.ExitWriteLock()

    'anything reading from this would need to have the following
    readerWriterLock.EnterReadLock()
    'logic
    readerWriterLock.ExitReadLock()

Попробуйте это, а затем, если не удастся, опубликуйте сообщение об исключении и любую другую информацию, которую сможете.

1 голос
/ 13 февраля 2011

Я считаю, что ваша самая большая проблема - не знать, какие функции в .Net являются поточно-ориентированными. Список, например, нет (словарь есть). Хотя вам это может сойти с рук, у вас могут возникнуть проблемы с блокировкой и т. Д.

Вы используете классы и переменные, которые не являются потокобезопасными. Каждый раз, когда вы работаете с потоками, вы должны быть предельно осторожны с блокировками. Чтобы ответить на ваш вопрос, да, вам нужно заблокировать и разблокировать все, с чем вы работаете, если только тип / метод не обрабатывает его специально для вас.

В .Net 4.0 существует много многопоточности (например, PLINQ), которые выполняют большую часть "тяжелой работы" для вас. Хотя вы должны научиться и понимать, как создавать потокобезопасный код самостоятельно, это даст вам преимущество.

Попробуйте передать данные в метод createXML (). Это может помочь изолировать код от других данных, к которым осуществляется доступ. Я бы посоветовал почитать о многопоточности и научиться делать это без фонового рабочего.

Глобальные переменные, как правило, плохая идея. Учитывая ваш код VB, я предполагаю, что это перенос из мира VB6 для вас. Это никоим образом не должно быть оскорбительным, просто пытаться продвинуть свои навыки вперед. Переменная область должна быть максимально ограниченной.

Еще одна мысль, касающаяся вашего кода, заключается в том, чтобы научиться использовать String.Format () при построении строк / путей.

Простая ручная тема в VB, чтобы вы начали:

Dim bThread As New Threading.Thread(AddressOf createXML)
bThread.IsBackground = True
bThread.Start()
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...