0

i am working with a file. this is code:

 Private Sub WriteXml(ByVal txtName As String)

    If Not Directory.Exists("GraphXml") Then
        Directory.CreateDirectory("GraphXml")
    End If

    _fileName = "GraphXml\Graph_" & txtName & ".xml"

    Dim checkCondition As Boolean = False
    _file = My.Computer.FileSystem.OpenTextFileWriter(_fileName, False)

    _file.WriteLine("<?xml version=""1.0"" encoding=""UTF-8""?>")

    _file.WriteLine("<n0>")

    DepthFirstSearch(StaticService.AllNodes(0))

    _file.WriteLine("</n0>")
    _file.Close()
    _file.Dispose()
End Sub

This method is called when button is clicked. If i do 1 click per 2 seconds, gives error: "another process uses file" . I could not understand the problem because i use file.close . I thought this may be relevant with threading problem and i asked this question link: and i tried with thread. code like this:

when a method is called , which thread will be run in c# and java?

and i tried with thread. code like this:

Dim thread As Threading.Thread = Nothing
Public Sub CreateXml()

    'cok hızlı tıklandıgı zaman xml olusturmak için çalışan thread önceki thread in file.close yapmasını bekler
    '   If Not checkThread Then


    Dim txtName As String = InputTxt.Items(InputTxt.SelectedIndex)
    txtName = txtName.Substring(0, txtName.IndexOf("."))

    While Not IsNothing(thread) AndAlso thread.IsAlive
        Dim a = ""
        ' wait loop
    End While

    thread = New Threading.Thread(Sub() WriteXml(txtName))
    thread.IsBackground = False
    thread.Start()

End Sub

This is also not working. i could not find any suggestions. I am gonna wait for responds.

Thanks

Community
  • 1
  • 1
donmezburak
  • 159
  • 1
  • 13
  • Advice: You shouldn't create your own threads when you can simply use the `ThreadPool` instead (e.g. `ThreadPool.QueueUserWorkItem(…)`; or use the TPL (i.e. `Task` introduced in .NET 4). Creating threads is a very expensive operation. – stakx - no longer contributing Sep 19 '14 at 15:43
  • Question: How long does it take `WriteXml` to write the file? You say you're clicking the button once every two seconds, but is the writing process actually taking much less time than that? – stakx - no longer contributing Sep 19 '14 at 15:44
  • I realized that it takes about 10-15 ms. However, i think close() method does not respond quickly. – donmezburak Sep 19 '14 at 21:23
  • Your code is not exception-safe. One mishap and a Try/Catch that swallows it and the show is over. It is very important to learn how to use the *Using* statement. – Hans Passant Sep 22 '14 at 11:26

1 Answers1

0

Obviously if you run the code simultaneously in two threads you get the concurrency error as the second thread tries to open the file in already in use by the first thread. You need a synchronization based on the file name, for example. Another solution would be disabling the button while running the thread and enable it again when finished processing.

In this particular case (about just two seconds), you should not mess with threads at all. Just replace following snippet from your code with in-place call of the method:

thread = New Threading.Thread(Sub() WriteXml(txtName))
thread.IsBackground = False
thread.Start()

Replace with:

WriteXml(txtName)

This way, the call to WriteXml would block the UI thread until finished, and user would not have chance to click the button twice.

George Polevoy
  • 7,450
  • 3
  • 36
  • 61
  • Good idea. However, i could not understand the two threads. When i click button, i heard that gui thread runs. am i right ? if so, why two thread occurs ? – donmezburak Sep 19 '14 at 21:22
  • Extra threads, besides the GUI thread, appear because you explicitly create them: New Threading.Thread. The first one appears when you click the first time, the second one appears as you click again. If the first thread have not finish yet, then you get two threads. – George Polevoy Sep 22 '14 at 11:12