Question Hangman problem

RyanHecht

New member
Joined
Sep 26, 2012
Messages
4
Location
Mt. Sinai, NY
Programming Experience
1-3
Hey, I'm 14, and fairly new to vb.net, having started a class in high school a couple weeks ago, and have been learning things as I've been going along. My most recent endeavor is a hangman game. I am designing a function to check whether a letter (guess) is contained in the secret word (HangWord), and then checks for occurrences of that word and replaces it in the form with the guess (lblword is the label it is changing, currently it would have "_" for each blank space (ignore the "DEBUGS", they're for, uh, debugging). The guess processes, and if the guess is correct the first part of the If statement runs. However, lblword.text does not change for the guess. If there are any more details that must be given, let me know and I will provide them. This is my first post on this forum, and I've only been using vb.net for about a month. If you introduce something not in the code currently, please include an explanation about it, so I can learn what it does, instead of blind copy/pasting. Also, I am not looking to change any mechanics of the game too drastically lol. Thanks, hope you guys can help!

Here is the body of the function I am desinging:
VB.NET:
    If InStr(HangWord, Guess) Then            
            DEBUG2.Text = Guess
            While counter <= WordLength
                If HangWord(counter) = Guess Then
                    Replace(lblword.Text, Guess, counter, 1)
                End If
                counter = counter + 1


            End While


        Else
            lblWrong.Text = lblWrong.Text + Guess & " "
            misses = misses + 1
            If misses = 1 Then
                board.Text = "  +---+ " & vbCrLf & _
      "  |   |" & vbCrLf & _
      "  O   |" & vbCrLf & _
      "      |" & vbCrLf & _
      "      |" & vbCrLf & _
      "      |" & vbCrLf & _
    "========="
            ElseIf misses = 2 Then
                board.Text = "  +---+  " & vbCrLf & _
                    "  |   |" & vbCrLf & _
                    "  O   |" & vbCrLf & _
                    "  |   |" & vbCrLf & _
                    "      |" & vbCrLf & _
                    "      |" & vbCrLf & _
                    "========="
            ElseIf misses = 3 Then
                board.Text = "  +---+  " & vbCrLf & _
                    "  |   |" & vbCrLf & _
                    "  O   |" & vbCrLf & _
                    " /|   |" & vbCrLf & _
                    "      |" & vbCrLf & _
                    "      |" & vbCrLf & _
                    "========="
            ElseIf misses = 4 Then
                board.Text = "  +---+  " & vbCrLf & _
                    "  |   |" & vbCrLf & _
                    "  O   |" & vbCrLf & _
                    " /|\  |" & vbCrLf & _
                    "      |" & vbCrLf & _
                    "      |" & vbCrLf & _
                    "========="
            ElseIf misses = 5 Then
                board.Text = "  +---+  " & vbCrLf & _
                    "  |   |" & vbCrLf & _
                    "  O   |" & vbCrLf & _
                    " /|\  |" & vbCrLf & _
                    " /    |" & vbCrLf & _
                    "      |" & vbCrLf & _
                    "========="
            ElseIf misses = 6 Then
                board.Text = "  +---+  " & vbCrLf & _
                    "  |   |" & vbCrLf & _
                    "  O   |" & vbCrLf & _
                    " /|\  |" & vbCrLf & _
                    " / \  |" & vbCrLf & _
                    "      |" & vbCrLf & _
                    "========="
                lblLose.Visible = True
                btnEnd.Visible = True
            End If


        End If
 
Hi RyanHecht,

Well done young programmer for a great effort after such little time programming. I have reviewed your code and made quite a few changes (trying not to change your code too much) to get the result you were after. Have a look at the code below and the comments that go with it. I hope I have explained things clearly enough but please do post back if you are unsure about anything.

VB.NET:
  Private Sub CheckLetter(Guess As String)
    Dim hangword As String = "Hangman"
    'Dim guess As String = String.Empty
    Dim counter, misses As Integer
    'Dim wordlength As Integer
 
    'If InStr(hangword, guess) Then
    'InStr is old VB. New VB.NET has the contains method to check for existence of a string within a string
    'I also use ToLower here as well to make sure that case sensitivity is ignored
    If hangword.ToLower.Contains(Guess.ToLower) Then
      'DEBUG2.Text = Guess
      'you do not need a variable Wordlength because you can just use the Length property of the string class
      'While counter <= wordlength
      While counter <= hangword.Length - 1
        'hangword(counter) returns a CHAR type does not easily expose the method ToLower and therefore is not good to accommodate case sensitivity
        'I have used the SubString method of the string class instead since it does expose the ToLower method of the string class
        'If hangword(counter) = Guess Then
        If hangword.Substring(counter, 1).ToLower = Guess.ToLower Then
          'Your biggest error here is that when you used the replace function you forgot to assign the result of the function back to the lblWord.text property
          'There are two ways you can use replace as you have it below barring your slight error.
          'Method 1
          'Replace(lblWord.Text, Guess, counter, 1) - You forgot the underscore to search for. Replace should have been defined as:-
          'Replace(lblWord.Text, "_", Guess, counter, 1) 
          'or
          'Method 2
          'lblWord.Text.Replace(<SearchCharacter>,<ReplaceCharacter>)
          'However neither of these methods actually work for you due to the following:-
          'In Method 1 your counter defines the starting point of your replacement string which when assigned back to lblWord.Text 
          'it truncates the starting portion of your string which you do not want
          'In Method 2 the Replace method replaces all instances of the searched for string with the replacement string which is also not what you want
 
          'to accommodate these issues I have used the SubString method exposed by the string class
          'It may seem a bit complicated at first sight but its really easy when you break it down to what is happening
          'Step 1
          'lblWord.Text = - make sure you assign the resulting string back to lblWord.Text
          'Step 2
          'lblWord.Text.Substring(0, counter) - Get the string before the position of the character to change
          'Step 3
          '& Guess - Add the character in the correct position of the string
          'Step 4
          '& lblWord.Text.Substring(counter + 1, lblWord.Text.Length - (counter + 1)) - Get the string after the position of the character to change
          lblWord.Text = lblWord.Text.Substring(0, counter) & Guess & lblWord.Text.Substring(counter + 1, lblWord.Text.Length - (counter + 1))
        End If
        counter = counter + 1
      End While
    Else
 
      lblWrong.Text = lblWrong.Text + Guess & " "
      'a shortcut for misses = misses + 1 in VV.NET is misses += 1
      misses = misses + 1
      'Using If is fine but just for information you could have also considered a case statement here
      'Select Case misses
      '  Case 1
      'do work here
      '  Case 2
      'do work here
      '  Case 3 'etc()
      'End Select
      If misses = 1 Then
        Board.Text = "  +---+ " & vbCrLf & _
                     "  |   |" & vbCrLf & _
                     "  O   |" & vbCrLf & _
                     "      |" & vbCrLf & _
                     "      |" & vbCrLf & _
                     "      |" & vbCrLf & _
                     "========="
      ElseIf misses = 2 Then
        Board.Text = "  +---+  " & vbCrLf & _
                     "  |   |" & vbCrLf & _
                     "  O   |" & vbCrLf & _
                     "  |   |" & vbCrLf & _
                     "      |" & vbCrLf & _
                     "      |" & vbCrLf & _
                     "========="
      ElseIf misses = 3 Then
        Board.Text = "  +---+  " & vbCrLf & _
                     "  |   |" & vbCrLf & _
                     "  O   |" & vbCrLf & _
                     " /|   |" & vbCrLf & _
                     "      |" & vbCrLf & _
                     "      |" & vbCrLf & _
                     "========="
      ElseIf misses = 4 Then
        Board.Text = "  +---+  " & vbCrLf & _
                     "  |   |" & vbCrLf & _
                     "  O   |" & vbCrLf & _
                     " /|\  |" & vbCrLf & _
                     "      |" & vbCrLf & _
                     "      |" & vbCrLf & _
                     "========="
      ElseIf misses = 5 Then
        Board.Text = "  +---+  " & vbCrLf & _
                     "  |   |" & vbCrLf & _
                     "  O   |" & vbCrLf & _
                     " /|\  |" & vbCrLf & _
                     " /    |" & vbCrLf & _
                     "      |" & vbCrLf & _
                     "========="
      ElseIf misses = 6 Then
        Board.Text = "  +---+  " & vbCrLf & _
                     "  |   |" & vbCrLf & _
                     "  O   |" & vbCrLf & _
                     " /|\  |" & vbCrLf & _
                     " / \  |" & vbCrLf & _
                     "      |" & vbCrLf & _
                     "========="
        lblLose.Visible = True
        btnEnd.Visible = True
      End If
    End If
    'Share()
  End Sub

Good luck and keep up the good work.

Cheers,

Ian
 
Ian,
Thank you very much for your help, I have learned a lot from your reply (especially using .contains instead of instr). However, my function still does not seem to be working. Here is the code, perhaps I forgot something you typed or inputted it incorrectly.

VB.NET:
Private Sub CheckLetter(ByVal Guess As String)        
            If HangWord.ToLower.Contains(Guess.ToLower) Then
            DEBUG2.Text = Guess
            While counter <= HangWord.Length - 1
                If HangWord.Substring(counter, 1).ToLower = Guess.ToLower Then
                    lblword.Text = lblword.Text.Substring(0, counter) & Guess & lblword.Text.Substring(counter + 1, lblword.Text.Length - (counter + 1))
                End If
                counter = counter + 1
            End While


        Else
            lblWrong.Text = lblWrong.Text + Guess & " "
            misses = misses + 1
            If misses = 1 Then
                board.Text = "  +---+ " & vbCrLf & _
      "  |   |" & vbCrLf & _
      "  O   |" & vbCrLf & _
      "      |" & vbCrLf & _
      "      |" & vbCrLf & _
      "      |" & vbCrLf & _
    "========="
            ElseIf misses = 2 Then
                board.Text = "  +---+  " & vbCrLf & _
                    "  |   |" & vbCrLf & _
                    "  O   |" & vbCrLf & _
                    "  |   |" & vbCrLf & _
                    "      |" & vbCrLf & _
                    "      |" & vbCrLf & _
                    "========="
            ElseIf misses = 3 Then
                board.Text = "  +---+  " & vbCrLf & _
                    "  |   |" & vbCrLf & _
                    "  O   |" & vbCrLf & _
                    " /|   |" & vbCrLf & _
                    "      |" & vbCrLf & _
                    "      |" & vbCrLf & _
                    "========="
            ElseIf misses = 4 Then
                board.Text = "  +---+  " & vbCrLf & _
                    "  |   |" & vbCrLf & _
                    "  O   |" & vbCrLf & _
                    " /|\  |" & vbCrLf & _
                    "      |" & vbCrLf & _
                    "      |" & vbCrLf & _
                    "========="
            ElseIf misses = 5 Then
                board.Text = "  +---+  " & vbCrLf & _
                    "  |   |" & vbCrLf & _
                    "  O   |" & vbCrLf & _
                    " /|\  |" & vbCrLf & _
                    " /    |" & vbCrLf & _
                    "      |" & vbCrLf & _
                    "========="
            ElseIf misses = 6 Then
                board.Text = "  +---+  " & vbCrLf & _
                    "  |   |" & vbCrLf & _
                    "  O   |" & vbCrLf & _
                    " /|\  |" & vbCrLf & _
                    " / \  |" & vbCrLf & _
                    "      |" & vbCrLf & _
                    "========="
                lblLose.Visible = True
                btnEnd.Visible = True
            End If


        End If
    End Sub

Thank you for all your help so far, hopefully you can tell me what I'm doing wrong this time!

Thanks,
Ryan
 
Hi Ryan,

I have tested your code and it works fine at my end so lets check a couple of things:-

1) Based on your first comments, when starting the Hangman game I have set the lblWord.Text string to the correct number of underscores for each character that makes up the word to be found. i.e. If you are finding the word "hangman" then lblWord.Text has to start with "_______". Can you check that you have done this when you start the game because if this is empty the .SubString methods that we have used will fail and the program will drop out.

2) If point 1 is no good then put a Try / Catch statement around the while statement to see if we can find out what's going wrong. i.e:-

VB.NET:
Try
  while......
    'all your while code here.....
  End While
Catch
  MsgBox(ex.message)
End Try
Let me know how it goes.

Cheers,

Ian
 
Ian,

Shortly after sending my reply, the power went out at my house and I decided to pass the time experimenting with the code. I found a very simple fix that I can't believe I didn't see before! the counter variable had been set earlier in the code (i didn't use a function to pick the HangWord, Just kinda put it in manually...counter was set there to make the "_"s in lblword already) so all I had to do was set counter back to 0, and everything worked again! I meant to edit my reply before you responded, but the power had not yet come on. Thank you for all of your help, I've learned a lot from this, and I'm looking forward to learning more in VB.net!

Thank you very much,

Ryan
 
Back
Top