Beefy Boxes and Bandwidth Generously Provided by pair Networks
P is for Practical
 
PerlMonks  

Re^5: Why does my get_max_index function return zero? (High Water Mark Algorithm)

by Marshall (Canon)
on Jun 04, 2019 at 22:17 UTC ( [id://11100977]=note: print w/replies, xml ) Need Help??


in reply to Re^4: Why does my get_max_index function return zero? (High Water Mark Algorithm)
in thread Why does my get_max_index function return zero? (High Water Mark Algorithm)

Ok, I don't see an obvious way using the flip-flop operator....Please enlighten us...

This idea using reduce which essentially has the equivalent of a foreach index did occur to me:

use strict; use warnings; use List::Util qw(reduce); my @arr = qw(0 3 5 12 3 2 1);; my $maxi = reduce { $arr[$a] > $arr[$b] ? $a : $b } (0..@arr-1); print "maximum i = $maxi value=$arr[$maxi]\n"; # maximum i = 3 value=12
Oh, and yes I almost always use @array-1 instead of $#array because I tend to either forget the right characters or type it somehow wrong.
  • Comment on Re^5: Why does my get_max_index function return zero? (High Water Mark Algorithm)
  • Download Code

Replies are listed 'Best First'.
Re^6: Why does my get_max_index function return zero? (High Water Mark Algorithm)
by holli (Abbot) on Jun 05, 2019 at 20:05 UTC
    use strict; use warnings; sub get_max_index { my $imax = 0; foreach (@_) { $imax = ($0 .. !$0) if $_ > $_[$imax]; } return $imax; } my @arr = (1,2,13,4,5); my $ans = get_max_index(@arr); print"$ans\n"; #2
    Such practices are better reserved for obfuscation purposes though, or if you want to show off.


    holli

    You can lead your users to water, but alas, you cannot drown them.
      Wow! I've looking at this and admit that I am at a loss to understand how it works. I see that it does indeed work, but even with some extra print statements, I'm not sure exactly how.

      I'd appreciate some enlightenment. ($0 .. !$0) is truly bizarre looking!
      update: How does the scalar value of the weird looking range wind up being one less when the "if statement" is satisfied as opposed to what it is before the if statement? Of course $0 is normally the file name of the executing Perl script (C:/...baha/../../this.pl) I don't understand the meaning of ($0 .. !$0).

      use strict; use warnings; $|=1; # turn of stdout buffering sub get_max_index { my $imax = 0; foreach (@_) { print "b4 if: default var = $_ imax=$imax\n"; print "b4 if: Value of weird range=".($0 .. !$0),"\n"; $imax = ($0 .. !$0), print "If triggered, new imax=$imax\n" if + $_ > $_[$imax]; print "\n"; } return $imax; } my @arr = (1,2,13,4,5); my $ans = get_max_index(@arr); print"$ans\n"; #2 __END__ b4 if: default var = 1 imax=0 b4 if: Value of weird range=1 b4 if: default var = 2 imax=0 b4 if: Value of weird range=2 If triggered, new imax=1 b4 if: default var = 13 imax=1 b4 if: Value of weird range=3 If triggered, new imax=2 b4 if: default var = 4 imax=2 b4 if: Value of weird range=4 b4 if: default var = 5 imax=2 b4 if: Value of weird range=5 2
        I am at a loss to understand how it works

        I was, too... though I'm closer than I was when it was first posted. After some more experimenting and reading on the flip-flop, here's what I think is happening. $0 will always be true, and thus !$0 will always be false. So the flipflop statement is thus TRUE .. FALSE. Since perlop says, "The value returned is either the empty string for false, or a sequence number (beginning with 1) for true", then the .. will start counting up, and since !$0 is always false, will never stop counting.

        My mental thinking is still wrong, however, because I'm still seeing an off-by-one error. On the second instance of that loop, I would expect the .. to return a 2, not a 1 -- as you showed, weird range was 2, but imax was 1...

        C:\berrybrew\5.30.0_64>perl -e "$foo = 'something true-ish'; foreach ( +0..9) { $bar = ($foo .. !$foo); print qq($bar:); }" 1:2:3:4:5:6:7:8:9:10:


        holli

        You can lead your users to water, but alas, you cannot drown them.

        But note also:

        c:\@Work\Perl\monks>perl -wMstrict -le "sub get_max_index { my $imax = 0; foreach (@_) { $imax = ($0 .. !$0) if $_ > $_[$imax]; print 'imax ', $imax; } return $imax; } my @arr = (1,2,13,4,5, 99); my $ans = get_max_index(@arr); print $ans; " imax 0 imax 1 imax 2 imax 2 imax 2 imax 3 3


        Give a man a fish:  <%-{-{-{-<

      This should be indexed by the Holli Inquisition. I wonder how you figured it out. Jesuitical question: Can you explain why it probably doesn’t work with 1..0 😎 ? And didn’t you get some warnings like ...uninitalized value...? Best regards, Karl

      «The Crux of the Biscuit is the Apostrophe»

      perl -MCrypt::CBC -E 'say Crypt::CBC->new(-key=>'kgb',-cipher=>"Blowfish")->decrypt_hex($ENV{KARL});'Help

        Can you explain why it probably doesn’t work with 1..0?

        Actually, it works without warnings for 1..0 or any other unequal pair of numbers (actually, it doesn't work at all per this, but at least it not-works consistently | actually, it isn't that consistent (update: see this)):

        c:\@Work\Perl\monks>perl -wMstrict -le "sub get_max_index { my $imax = 0; ;; foreach (@_) { $imax = (1 .. 0) if $_ > $_[$imax]; } return $imax; } ;; $. = 1; ;; my @arr = (1,2,13,4,5); my $ans = get_max_index(@arr); print qq{i max == $ans; \@arr[$ans] == $arr[$ans]}; " i max == 2; @arr[2] == 13
        (Update: Try this with  my @arr = (1,2,13,4,5, 99); as the test input to see it not-work.)

        Note the  $. = 1; statement. Per Range Operators in perlop:

        If either operand of scalar ".." is a constant expression, that operand is considered true if it is equal ("==") to the current input line number (the $. variable).
        So the following flip-flop values and  $. initializations "work":
        • $imax = (  1 ..   0) if $_ > $_[$imax]; for  $. = 1
        • $imax = (  0 ..   1) if $_ > $_[$imax]; for  $. = 0
        • $imax = ( 42 .. 137) if $_ > $_[$imax]; for  $. = 42
        • $imax = (137 ..  42) if $_ > $_[$imax]; for  $. = 137

        And yes, this sort of thing should definitely appear in some sort of index of heretical teachings, somewhere.


        Give a man a fish:  <%-{-{-{-<

Log In?
Username:
Password:

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: note [id://11100977]
help
Chatterbox?
and the web crawler heard nothing...

How do I use this?Last hourOther CB clients
Other Users?
Others drinking their drinks and smoking their pipes about the Monastery: (3)
As of 2024-04-24 01:31 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found