943,772 Members | Top Members by Rank

Ad:
  • Perl Discussion Thread
  • Unsolved
  • Views: 801
  • Perl RSS
Feb 1st, 2009
0

perl arrays

Expand Post »
im working with some perl code, and im really unfamiliar with the language, and I have a situation. I'm working with a package of perl scripts for a game, there are about 4000 of them and counting. They are release constantly, and altering their contents isnt really an option, it would just be too time consuming. That being said, here is an example of one that fits the situation i'm having.

Perl Syntax (Toggle Plain Text)
  1. sub EVENT_ITEM {
  2. if($item1=="7880" && $item2=="7879" && $item3=="5192"){
  3. quest::summonitem(4199);
  4. quest::exp(85); }
  5. }

This would normally be executed by the video game that would supply the EVENT_ITEM call, ass well as the summonitem, and exp functions.

I'm simmulating this invlovement on my site. There is a perl script that executes the EVENT_ITEM sub, and there are provodided summonitem and exp functions that instead spit out HTML that is returned to my php for display.

In essence they are able to simmulate game activities on the webpage before they try for real in the game.

The situation im having is with the $item1-$item4. They are hardcoded in the scripts(the ones i can't change). On the site, I will have 4 textboxes where they person can type these values in and submit them to the perl script. The issue is... if the user puts them in the wrong order the conditional wont execute. They might put item# 7880 in the 3rd box... and then it wouldnt function.

my question is this: Is there someway I can load multiple values into $item1-$item4? Something to the effect of an array that will evaluate every single value in a conditional. For instance in my main perl file that will simmulate execution of the EVENT_ITEM could I do something like

Perl Syntax (Toggle Plain Text)
  1. $item1=array(7880,7879,5192)
  2. $item2=array(7880,7879,5192)
  3. $item3=array(7880,7879,5192)

So when $item1==7880 it will check all three values before returning its true/false. Anyone got any idea?


Sorry for the length, i know im long winded.
Similar Threads
Reputation Points: 10
Solved Threads: 0
Junior Poster in Training
headedtomexico is offline Offline
55 posts
since Jan 2009
Feb 2nd, 2009
0

Re: perl arrays

There is probably a cleaner and easier way to do this, but if you include this sub in your perl file somewhere:
perl Syntax (Toggle Plain Text)
  1. sub Compare_Items
  2. {
  3. ($ref_cmplist, $ref_udata) = @_;
  4.  
  5. foreach $udata (@{$ref_udata}) {
  6. $flags{$udata} = false;
  7. foreach $cmp_item (@{$ref_cmplist}) {
  8. if ($cmp_item eq $udata) { $flags{$udata} = true; }
  9. }
  10. }
  11.  
  12. while (($key, $value) = each %flags) {
  13. if ($value eq false) { $main_flag = false; }
  14. }
  15.  
  16. return $main_flag;
  17. }
Then you can use it by simply checking its return value. First however, there are a couple of things I should mention. There needs to be 2 arrays in order for this to work. The good news, is that this is very flexible, and can handle many arguments (not just limited to item1, item2, etc). This is basically what you need to do... make an array, which is the list of values you want to compare the user entered values against. In your example, that array would need to contain "7880", "7879", and "5192". Then, you need to take the scalars entered by the user (ie: $item1, $item2, $item3) and put those into an array. Then pass both arrays to the sub/function above. It sounds a lot more complicated than it is really. Here is the code that I used, commented and in its entirety (the code is much shorter without all the comments ):
perl Syntax (Toggle Plain Text)
  1. $main_flag = true;
  2.  
  3. $item1 = "7880"; # Input Would Be From Textbox, Not Assigned Like Here
  4. $item2 = "5192"; # Input Would Be From Textbox, Not Assigned Like Here
  5. $item3 = "7879"; # Input Would Be From Textbox, Not Assigned Like Here
  6.  
  7. # // This Is The List Of Items That You Want
  8. # // To Compare The User Input Against
  9. push @compare_list, "7880";
  10. push @compare_list, "7879";
  11. push @compare_list, "5192";
  12.  
  13. # // Here, We Actually Put $item1, $item2 And $item3
  14. # // Into An Array.... Yeah, It's That Easy
  15. push @userdata, $item1;
  16. push @userdata, $item2;
  17. push @userdata, $item3;
  18.  
  19.  
  20. # // Now We Call The Sub, And Pass It References
  21. # // To Both Of The Arrays. When This Line Finishes
  22. # // The Variable "$are_same" Will Be Either True
  23. # // Or False... True If All The Items Match Something
  24. # // From The Other List... False If Even One Does Not
  25. # // Match.
  26. $are_same = &Compare_Items( \@compare_list, \@userdata );
  27.  
  28. # // Display True Or False To The Screen
  29. # // ie: Do The Items All Match?
  30. # // You Should Probably Test This With
  31. # // An If, Instead Of Showing Its Value ;-)
  32. print "$are_same\n";
  33.  
  34. exit;
  35.  
  36. sub Compare_Items
  37. {
  38. ($ref_cmplist, $ref_udata) = @_;
  39.  
  40. foreach $udata (@{$ref_udata}) {
  41. $flags{$udata} = false;
  42. foreach $cmp_item (@{$ref_cmplist}) {
  43. if ($cmp_item eq $udata) { $flags{$udata} = true; }
  44. }
  45. }
  46.  
  47. while (($key, $value) = each %flags) {
  48. if ($value eq false) { $main_flag = false; }
  49. }
  50.  
  51. return $main_flag;
  52. }
let me know if you need further assistance, or if this just doesn't do what you expect or need.
Last edited by Comatose; Feb 2nd, 2009 at 1:11 am.
Team Colleague
Reputation Points: 361
Solved Threads: 214
Taboo Programmer
Comatose is offline Offline
2,413 posts
since Dec 2004
Feb 2nd, 2009
0

Re: perl arrays

I don't think that would do it. Lemme give you a better example of whats being run here.

Perl Syntax (Toggle Plain Text)
  1. $item1=$ARGV[0];
  2. $item2=$ARGV[1];
  3. $item3=$ARGV[2];
  4. $item4=$ARGV[3];
  5. $myscript=$ARGV[3];
  6.  
  7. my $TheQuest="";
  8.  
  9. sub WriteIt {
  10. $TheQuest.=$_[0]."\n";
  11. }
  12.  
  13. sub exp {
  14. WriteIt("<br><font color=yellow>You gain experience!!</font>");
  15. }
  16.  
  17. sub summonitem {
  18. WriteIt("<br><b>".$myscript." gives you : </b><a href=$main::root_url"."item.php?id=$_[0]>".$_[0]."</a>");
  19. }
  20.  
  21. eval "require '$myscript'";
  22.  
  23. EVENT_ITEM();
  24.  
  25. print $TheQuest;
  26. exit;
  27. }


ok, so i've got the like 4000 files that this gets run on, and the contents will vary greatly. There really isn't any way for me to predict what item numbers are going to be in the game characters file. So i'll give two scenarios.

The player wants to simmulate giving items to King Tormax to see if his quest is working. So they come to my site, and "give" him 3 items to see if his quest is working. The php calls my perl with all the arguments as follow. "'questparser.pl' '7880' '7879' '5192' '0' 'King_Tormax.pl'"

This will end up including the King_Tormax file, which will have the EVENT_ITEM in it, and the calls to item1-item4. In this situation the items are set in the correct order for king tormax's quest file. which is as follows

Perl Syntax (Toggle Plain Text)
  1. sub EVENT_ITEM {
  2. if($item1=="7880" && $item2=="7879" && $item3=="5192"){
  3. quest::summonitem(4199);
  4. quest::exp(85); }
  5. }

had they typed the items in a different oder, 7879, 7880, 5192, then the conditional in king tormax's file wouldnt go off. In the actual game the items are handed in all at once, so order is not a factor, and a user wouldnt expect it to be a factor on my site. Furthermore the quest files for each game character aren't written with the arguments in any kind of order. In this example they are in descending order, but its pure coincidence.

Another example is Veltar,
Perl Syntax (Toggle Plain Text)
  1. sub EVENT_ITEM {
  2. if($item1=="356" && $item2=="685"){
  3. quest::say("Very well mortal...");
  4. quest::summonitem(376);
  5. quest::exp(1000); }
  6. elseif($item1=="2296" && $item2=="686"){
  7. quest::say("You have done well for me!");
  8. quest::summonitem(377);
  9. quest::exp(1000); }


as you can see, its very chaotic what to expect from the quest files. In game im really not sure how they do it. When you give the items to the game character a window opens up with 4 slots, and you hand the items in, in any order. So i'm not sure how the game server, which is written in c++, calls the perl so that these items are in order. Naturally the say, summonitem, exp functions are all provided by the game server in that case. These are the things i'm simmulating by writing my own functions that output html.

I was wondering if there was some kind of regular expression that could be used to do this. I've never really messed with the stuff, but i've seen items in []'s before. Would something like

Perl Syntax (Toggle Plain Text)
  1. $item1="/[".$ARGV[0].",".$ARGV[1].",".$ARGV[2].",".$ARGV[3]."]/"
  2. $item2="/[".$ARGV[0].",".$ARGV[1].",".$ARGV[2].",".$ARGV[3]."]/"
  3. $item3="/[".$ARGV[0].",".$ARGV[1].",".$ARGV[2].",".$ARGV[3]."]/"
  4. $item4="/[".$ARGV[0].",".$ARGV[1].",".$ARGV[2].",".$ARGV[3]."]/"

so when the conditional of $item1=="7880" fires it will check "/[7880,5192,7879,0]/=="7880"

I know none of that is syntactically correct im shooting in the dark =P
Reputation Points: 10
Solved Threads: 0
Junior Poster in Training
headedtomexico is offline Offline
55 posts
since Jan 2009
Feb 2nd, 2009
0

Re: perl arrays

I do believe the code I gave you above would work just fine for what you are doing... instead of manually using push to push each item, you would do a for loop and push all of the items that are arguments and that are not the last one (the filename). However, this can be done with grouping in regex similar to this:
perl Syntax (Toggle Plain Text)
  1. $item1 = "Fun";
  2. $retval = ($item1 =~ m/(Fun|Sucky|Cool)/i) ? true : false;
  3.  
  4. print "$retval\n";
This will set $retval to true or false depending on if $item1 contains any of the words in the group (Fun, Sucky or Cool) or not.
Team Colleague
Reputation Points: 361
Solved Threads: 214
Taboo Programmer
Comatose is offline Offline
2,413 posts
since Dec 2004
Feb 2nd, 2009
0

Re: perl arrays

Quote ...
so when the conditional of $item1=="7880" fires it will check "/[7880,5192,7879,0]/=="7880"
Its possible (I think). Using a hash sounds like the better approach. Very simple example:

Perl Syntax (Toggle Plain Text)
  1. %item1 = (
  2. 7880 => [7880,7879,5192,0],
  3. 7879 => [7879,7880,5192,0],
  4. 5192 => [5192,7880,7879,0],
  5. );
  6.  
  7. $item1 = $item1{$ARGV[0]} || die "Usage: no item found\n";

In the above if $ARGV[0] equaled 7880 then $item1 will be a reference to an array : [7880,7879,5192,0]. The first value is:

$item1->[0]

And so on for the other values in the array reference. The concept is pretty straight forward, but the implementation might not be.
Last edited by KevinADC; Feb 2nd, 2009 at 3:29 pm.
Reputation Points: 246
Solved Threads: 67
Practically a Posting Shark
KevinADC is offline Offline
898 posts
since Mar 2006
Feb 4th, 2009
1

Re: perl arrays

Seems that maybe headedtomexico is now madeittomexico
Reputation Points: 246
Solved Threads: 67
Practically a Posting Shark
KevinADC is offline Offline
898 posts
since Mar 2006
Feb 5th, 2009
0

Re: perl arrays

Use an perl array:

Perl Syntax (Toggle Plain Text)
  1. @array=("1234","4231","5674");
  2. print "$array[0]\n$array[1]\n$array[2]\n";
  3. for $var (@array){
  4. print "$var\n";
  5. }

You can pass the array to a sub or an object and the sub or or object will get the array in @_ or you can shift it into a local variable.
Reputation Points: 26
Solved Threads: 38
Posting Whiz in Training
mitchems is offline Offline
293 posts
since Feb 2009
Feb 5th, 2009
0

Re: perl arrays

...
Team Colleague
Reputation Points: 361
Solved Threads: 214
Taboo Programmer
Comatose is offline Offline
2,413 posts
since Dec 2004

This thread is more than three months old

No one has posted to this discussion for at least three months. Please let old threads die and do not reply to them unless you feel you have something new and valuable to contribute that absolutely must be added to make the discussion complete. Otherwise, please start a new thread in this forum instead.
Message:
Previous Thread in Perl Forum Timeline: perl/Cookie... basic question
Next Thread in Perl Forum Timeline: Date String Problem





About Us | Contact Us | Advertise | Acceptable Use Policy
Forum Index | Build Custom RSS Feed


Follow us on Twitter


© 2011 DaniWeb® LLC