Anonymous Monk has asked for the wisdom of the Perl Monks concerning the following question:

Hello Monks, I am havng a issue with an if statement. I have a sub funtion asking th e cusotmer a quesiton which then calls another sub funtion that just get's the user input. I have an if statement, if the answer doesn't equal Y or N, then prompt them again for an Y or N answer. It get's to the if statement and calls the autoSubmit function again, after the end user has answers the question wrong again, for some reason the program is dying and not prompting them again. Any ideas?
my $autoSubmit; sub autoSubmit{ print "Would you like the logs submitted? Y\\N?: "; $autoSubmit = getInput; return $autoSubmit; } autoSubmit; if(( lc($autoSubmit) ne "y") and ($autoSubmit ne "n")) { print "You did not enter in Yes or No. Please try again\n"; autoSubmit; }

Replies are listed 'Best First'.
Re: Recursive If statement not working.
by Transient (Hermit) on Jun 25, 2009 at 19:13 UTC
    It's because your if will only check once - you want a while loop.
    while (( lc($autoSubmit) ne "y") and ($autoSubmit ne "n")) { print "You did not enter in Yes or No. Please try again\n"; autoSubmit; }
    Updated: Changed language used
Re: Recursive If statement not working.
by kennethk (Abbot) on Jun 25, 2009 at 19:19 UTC
    In order for a call to be recursive, the function must be called from within itself. You do not do that here. If you want to keep a recursive structure, you could do something like:

    sub autoSubmit{ print "Would you like the logs submitted? Y\\N?: "; my $autoSubmit = getInput; if ( (lc($autoSubmit) ne "y") and ($autoSubmit ne "n")) { print "You did not enter in Yes or No. Please try again\n"; $autoSubmit = autoSubmit(); } return $autoSubmit; }

    However, recursion in this case seems like overkill to me, since you could just use a while loop to do the same thing:

    sub autoSubmit{ print "Would you like the logs submitted? Y\\N?: "; my $autoSubmit; while (1) { $autoSubmit = getInput; last if ( (lc($autoSubmit) eq "y") or ($autoSubmit eq "n")); print "You did not enter in Yes or No. Please try again\n"; } return $autoSubmit; }

    See last for some info on loop control.

Re: Recursive If statement not working.
by Old_Gray_Bear (Bishop) on Jun 25, 2009 at 19:28 UTC
    Look at your if statement  if(( lc($autoSubmit) ne "y") and ($autoSubmit ne "n"))--

    if $autoSubmit='Y'", the first clause of the AND statement is 'true' and the second clause is 'false'. The result of 'true' AND 'false' is 'false' and the control bypasses the if-block. Same argument applies for 'N' as well. Use OR logic for this.

    or use

    return(lc $autoSubmit) if (lc $autoSubmit eq 'y'); return(lc $autoSubmit) if (lc $autoSubmit eq 'n'); autoSubmit();
    Note: You can also us a while loop and get rid of the "subroutine" call.

    ----
    I Go Back to Sleep, Now.

    OGB

      Actually, the way that it is is correct, albeit it should be if ( (lc($autosubmit) ne "y") and (lc($autosubmit) ne "n") )

      Truth tables:
      p q ~p ~q p^q ~p v ~q ~( p ^ q ) T T F F T F F T F F T T F F F T T F T F F F F T T F T T
      where p = lc($autosubmit) eq "y" and q = lc($autosubmit) eq "n" if $autosubmit is "Y", then p is True and q is false (lc("Y") = "y" but lc("Y") does not equal "n"), thus the statement as a whole is false and we do not enter the loop. The only time the loop is activated is if both conditions fail ( that is $autosubmit is neither "y" nor "n" ). Conversely (or contrapositively, whatever the term is - I forget), the same could be written as:
      unless ( lc($autosubmit) eq "y" or lc($autosubmit) eq "n" )
      shown above as ~(p ^ q)

      Update: wow, I need to re-read - you come to the same conclusions, but it's just that the OP wants to bypass the "if" in that case (either y or n). So I posted truth tables in vain =) The issue here is that it will only be called once - on the first failure.