Tek-Tips is the largest IT community on the Internet today!

Members share and learn making Tek-Tips Forums the best source of peer-reviewed technical information on the Internet!

  • Congratulations bkrike on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

Global symbols requires explicit package name

Status
Not open for further replies.

TheDauntless

Programmer
Feb 26, 2008
14
BE
Hey,

I keep getting this error with the following code:
Code:
#!/usr/bin/perl -w
use strict;


sub mainMenu
{
    print "Kies een optie (1-7)\n";    
    &listenForMenuChoice;
}

sub listenForMenuChoice
{
    local($choice);
    $choice = <>;
    chop $choice;
    
    use Switch;
    switch ($choice)
    {
        case "1"
        {
            $status = 1;
            &startNewOrder;
        }
        case "1"
        {
            $status = 1;
            &startNewOrder;
        }
    }
    
}

# de huidige status waar de klant in zit (komt overeen met menu opties)
global $status = undef;

Why do I keep getting this error? I'm now getting it at the first 5 lines of 'listenForMenuChoice'.


It probably has something to do with variable scope, but I've been googling for a few hours now and I can't find a descent explanation....

All help is appreciated!
 
Code:
local($choice);
The 'local' function gives a temporary value to a global variable. But you're using strict and you haven't declared a global variable called $choice. That's why you're getting the error. You almost certainly want to use 'my' instead of 'local'.
 
Ah, I get it!

So I changed those lines to:
Code:
  my $choise = <>;
    chop my $choice;
And the error is gone. Now I get another error (well, same error, different place). I'm getting it at the $status = 1; in the switch. How can I access the global variable?

Also: is "glob $status = undef;" correct? I'm just using 'glob' 'cause that turned purple in my editor (just like 'my'). (The problem is still there if I change it to 'my $status = undef')
 
drop "my" in the second line, and you almost certainly want to use chomp instead of chop::

Code:
my $choice = <>;
chomp $choice;

or all in one line:

Code:
chomp(my $choice = <>);

declare $status at the beginning of the function:

Code:
sub listenForMenuChoice
{
   chomp(my $choice = <>);
   my $status;
   use Switch;
   switch ($choice)
    {
        case "1"
        {
            $status = 1;
            &startNewOrder;
        }
        case "1"
        {
            $status = 1;
            &startNewOrder;
        }
    }
    [red]return $status;[/red]  
}

You also have to use the return() function to return a value to the caller otherwise $status will not be visible to the rest of the script.

Why do you have the same case statement twice?


------------------------------------------
- Kevin, perl coder unexceptional! [wiggle]
 
I have the same case statement twice because I was in the middle of copy pasting when I posted the script :p.

Why do I need a return? I have declared '$status' in the main part (so not inside a routine). I just need to access THAT $status from within a routine. (Just like you would access instance variables from within a method (in an OO language))

CHOMP vs CHOP: I looked it up and I guess I better use CHOMP, but in this case it doesn't really mater (but I will change it)


I also have another question, but I'll create a new thread for that :)

Thank you for replying !
 
chomp vs. chop: it may not matter this time but when you try to move your script from a *nix platform to a Windows one you'll be scratching your head trying to figure out why it doesn't work anymore. Best get it right first time.
 
Ok, got that :).

But I still have a question concerning the scope issue. Little example:
Code:
my $status = 0;
sub sub1
{
my $status = 1;
&sub2;
}

sub sub2
{
print my $status;
}
&sub1;
The idea is that all those $status'es should point to the same $status (the one declared in line 1). How do I do that?
 
stop adding my after you've declared it once if you don't want to change to scope.
Code:
my $status = 0;
sub sub1
{
	$status = 1;
	&sub2;
}

sub sub2
{
	print $status;
}
&sub1;

#or quit mixing them up and just declare new variables in each subroutine which will probably save you headaches later anyway


Code:
my $status = 0;
sub sub1{
	my $input = shift @_;
	$input = 1;
	&sub2($input);
}

sub sub2{
	my $input2 = shift @_;
	print $input2;
}
&sub1($status);

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
[noevil]
Travis - Those who say it cannot be done are usually interrupted by someone else doing it; Give the wrong symptoms, get the wrong solutions;
 
By putting 'my' before each one, you're expressly creating a new variable each time! Just create the first one using "my" and then don't qualify your use of $status thereafter and you'll be referring to the same one each time.
 
If I don't write the 'my ' it gives the same error at that line.

Code:
my $status = undef;
sub listenForMenuChoice
{
    print "Geef uw keuze en druk op enter.\n";
    my $choice = <>;
    chop $choice;
    print "\n";
    
    use Switch;
    switch ($choice)
    {
        case "1"
        {
            $status = 1;
            &startNewOrder;
        }
}
}
It gives an error on the "$status = 1;" line.
 
what error does it give? Just saying it gives an error is useless information. The Switch module is buggy though, it often creates problems.

------------------------------------------
- Kevin, perl coder unexceptional! [wiggle]
 
The same error as before; the one in the topic title :)

"Global symbol XXXXX requires explicit package name"

I now tried this:
$Main::counter = 1;

That seems to help. Is this supposed to be used like that?
 
A quck test seems to work OK for me:

Code:
use strict;
use warnings;
my $status = undef;
listenForMenuChoice(1);
sub listenForMenuChoice
{
    print "Geef uw keuze en druk op enter.\n";
    my $choice = shift;
    chomp $choice;
    print "\n";
    
    use Switch;
    switch ($choice)
    {
        case "1"
        {
            $status = 1;
            print $status;
        }
    }
}

------------------------------------------
- Kevin, perl coder unexceptional! [wiggle]
 
You'd have to have declared $status using 'my' before the subroutine is declared, as opposed to just having it before your subroutine is called.
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top