Hello and welcome to our community! Is this your first visit?
Register
Enjoy an ad free experience by logging in. Not a member yet? Register.
Page 1 of 2 12 LastLast
Results 1 to 15 of 16
  1. #1
    Master Coder
    Join Date
    Apr 2003
    Location
    in my house
    Posts
    5,211
    Thanks
    39
    Thanked 201 Times in 197 Posts

    how to extend length of hash -tute plz

    Hi,

    I have a hash with three values and because I have got newly entered data I want to add to that hash. I don't mean build the hash but extend it.

    like this

    $stuff{$product_id}{$product_name}{$price};
    is to become this

    $stuff{$product_id}{$product_name}{$price}{$year_of_manufacture};

    So I have my hash:- %stuff but I can't seem to find how to add more columns/fileds to it.

    Any pointers or tutorials very welcome.

    I think I should just build a new hash but I wonder if there is an already better way.

    bazz
    Last edited by bazz; 08-18-2009 at 04:50 AM.
    "The day you stop learning is the day you become obsolete"! - my late Dad.

    Why do some people say "I don't know for sure"? If they don't know for sure then, they don't know!
    Useful MySQL resource
    Useful MySQL link

  • #2
    New Coder
    Join Date
    Jul 2009
    Posts
    43
    Thanks
    0
    Thanked 0 Times in 0 Posts
    Code:
    $stuff{$product_id}=$product_name;

    Code:
    for($i=0;$product_id;$i++){
       $stuff{$product_id[$i]}=$product_name[$i];
    }
    if you want a three dimensial or more arrays or hashes then u want something like this

    Code:
    @breakfast = ("Cheese","bread","Tuna");
    @lunch = ("chicken","rice");
    @tea = ("steak","water","fish");
    
    @today = (\@breakfast,\@lunch,\@tea);
    push @lunch,"soup";
    push @{$today[1]},"salad";
    
    $tea[1] = "hot $tea[1]";
    $today[3][0] = "milk";
    
    print $today[2][1],"\n";
    
    foreach $course (@today) {
            @this = @$course;
            print ".... @this\n";
            }
    not sure why u asking that.. arent u a senior code??

    DoubleThink
    Last edited by hackYourBrain; 08-18-2009 at 03:49 PM.

  • #3
    Super Moderator
    Join Date
    May 2005
    Location
    Southern tip of Silicon Valley
    Posts
    2,838
    Thanks
    2
    Thanked 160 Times in 155 Posts
    Your nesting is to deep. You should use a HoH, not a HoHoHoH.

    Example:
    Code:
    use Data::Dumper;
    
    %product = ( 123 => { name        => 'product1',
                          'yr_of_mfg' => 2003,
                          'price'     => 100,
                         },
                 231 => { name        => 'product2',
                          'yr_of_mfg' => 2005,
                          'price'     => 200,
                         },
                );
                
    # let's add another product;
    $product{321} = { name        => 'product3',
                      'yr_of_mfg' => 2007,
                      'price'     => 400,
                     };
    
    print Dumper \%product;
    Outputs:
    Code:
    $VAR1 = {
              '231' => {
                         'name' => 'product2',
                         'price' => 200,
                         'yr_of_mfg' => 2005
                       },
              '123' => {
                         'name' => 'product1',
                         'price' => 100,
                         'yr_of_mfg' => 2003
                       },
              '321' => {
                         'name' => 'product3',
                         'price' => 400,
                         'yr_of_mfg' => 2007
                       }
            };

  • #4
    New Coder
    Join Date
    Jul 2009
    Posts
    43
    Thanks
    0
    Thanked 0 Times in 0 Posts
    hmm.. interesting.

    NewLosAngeles
    Last edited by hackYourBrain; 08-19-2009 at 02:28 AM.

  • #5
    Super Moderator
    Join Date
    May 2005
    Location
    Southern tip of Silicon Valley
    Posts
    2,838
    Thanks
    2
    Thanked 160 Times in 155 Posts
    I left out an example.

    Lets say you want to "extend" the hash in my previous example, such as by adding a "manufacturer", here's an example of how to do it.

    Code:
    use Data::Dumper;
    
    %product = ( 123 => { name        => 'product1',
                          'yr_of_mfg' => 2003,
                          'price'     => 100,
                         },
                 231 => { name        => 'product2',
                          'yr_of_mfg' => 2005,
                          'price'     => 200,
                         },
                );
                
    # let's add another product;
    $product{321} = { name        => 'product3',
                      'yr_of_mfg' => 2007,
                      'price'     => 400,
                     };
    
    # lets "extend it"
    $product{321}{'manufacturer'} = 'company.com';
    
    print Dumper \%product;
    Outputs:
    Code:
    $VAR1 = {
              '231' => {
                         'name' => 'product2',
                         'price' => 200,
                         'yr_of_mfg' => 2005
                       },
              '123' => {
                         'name' => 'product1',
                         'price' => 100,
                         'yr_of_mfg' => 2003
                       },
              '321' => {
                         'manufacturer' => 'company.com',
                         'name' => 'product3',
                         'price' => 400,
                         'yr_of_mfg' => 2007
                       }
            };

  • #6
    Master Coder
    Join Date
    Apr 2003
    Location
    in my house
    Posts
    5,211
    Thanks
    39
    Thanked 201 Times in 197 Posts
    As ever FishMonger, that makes sense.

    Now it's time for real data variables.

    The two methods below build the hash differently. I think the second is the better (only) way. However, I would appreciate your comments because hashes have been a nightmare for me to grasp a hold of.

    This was the first way (since your last post).
    Code:
    $new_tariffs_hash{$live_product_id}{'age_data'}{$age_group}{$terms_abbr}{$terms}{$price}++;
    $new_tariffs_hash{$live_product_id}{'tariff_start_date'}=$tariff_start_date;
    $new_tariffs_hash{$live_product_id}{'tariff_end_date'}=$tariff_end_date;
    $new_tariffs_hash{$live_product_id}{'nights_on_first_tariff'} = $nights_on_first_tariff;
    $new_tariffs_hash{$live_product_id}{'nights_on_second_tariff'} = $nights_on_second_tariff;

    This is my most recent way and it is easier to follow the dumped output and may associate sufficiently well.

    Code:
    $new_tariffs_hash{$live_product_id}{'age_data'}{$age_group}{$terms_abbr}{$terms}=$price;
    $new_tariffs_hash{$live_product_id}{'tariff_start_date'}=$tariff_start_date;
    $new_tariffs_hash{$live_product_id}{'tariff_end_date'}=$tariff_end_date;
    $new_tariffs_hash{$live_product_id}{'nights_on_first_tariff'} = $nights_on_first_tariff;
    $new_tariffs_hash{$live_product_id}{'nights_on_second_tariff'} = $nights_on_second_tariff;
    This is the dumped output from the second code.

    Code:
    'tariffs_hash' => {
                           '84' => {
                                     'tariff_end_date' => '2010-03-31',
                                     'tariff_start_date' => '2009-10-01',
                                     'age_data' => {
                                                         'Adult' => {
                                                                       'pppns' => {
                                                                                      'Per Person Per Night Sharing ' => '32.50'
                                                                                   },
                                                                       'prpn' => {
                                                                                    'Per Room Per Night' => '65.00'
                                                                                 },
                                                                        'sopn' => {
                                                                                     'Single Occupancy Per Night' => '45.00'
                                                                                  }
                                                                       }
                                                        },
                                     'nights_on_second_tariff' => 0,
                                     'nights_on_first_tariff' => 5
                                   },
                                   
                         '85' => {
                                   'tariff_end_date' => '2009-09-30',
                                   'tariff_start_date' => '2009-08-01',
                                   'age_data' => {
                                                       'Adult' => {
                                                                     'pppns' => {
                                                                                    'Per Person Per night Sharing ' => '32.50'
                                                                                 },
                                                                     'prpn' => {
                                                                                  'Per Room Per Night' => '65.00'
                                                                               },
                                                                     'sopn' => {
                                                                                  'Single Occupancy Per Night' => '45.00'
                                                                                }
                                                                     }
                                                      },
                                   'nights_on_second_tariff' => 3,
                                   'nights_on_first_tariff' => 2
                                 },
                          '83'=>{
                                  'tariff_end_date' => '2009-09-30',
                                  'tariff_start_date' => '2009-08-01',
                                  'age_data' => {
                                                     'Up to 12 yrs' => {
                                                                            'pacpn' => {
                                                                                          'Per Accompanied Child Per Night' => '25.44'
                                                                                        }
                                                                             },
                                                     'Adult' => {
                                                                  'pppns' => {
                                                                                'Per Person Per Night Sharing ' => '30.00'     
                                                                              },
                                                                   'prpn' => {
                                                                               'Per Room Per Night' => '60.00'
                                                                             },
                                                                   'sopn' => {
                                                                                'Single Occupancy Per Night' => '40.00'
                                                                             }
                                                                  }
                                                  },
                                  'nights_on_second_tariff' => 3,
                                  'nights_on_first_tariff' => 2
                              }
                         },
    Is the second way how you would do it? I have still a bit of tweaking to do because I need to be able to show more than one start date, to be able to relate the pricing to the date.

    (I think I have been doing the usual and making life more difficult. I was trying to use the variables as the category name in the hash and when that wasn't possible, I built it too deeply).

    any advice you can give would be most welcome.

    bazz
    Last edited by bazz; 08-19-2009 at 08:38 AM.
    "The day you stop learning is the day you become obsolete"! - my late Dad.

    Why do some people say "I don't know for sure"? If they don't know for sure then, they don't know!
    Useful MySQL resource
    Useful MySQL link

  • #7
    Master Coder
    Join Date
    Apr 2003
    Location
    in my house
    Posts
    5,211
    Thanks
    39
    Thanked 201 Times in 197 Posts
    OK, I have made the hash where the $value is a string of the required, associated data. should be simple enough to split it in the 'while' loop and to use it as required.

    bazz
    "The day you stop learning is the day you become obsolete"! - my late Dad.

    Why do some people say "I don't know for sure"? If they don't know for sure then, they don't know!
    Useful MySQL resource
    Useful MySQL link

  • #8
    Master Coder
    Join Date
    Apr 2003
    Location
    in my house
    Posts
    5,211
    Thanks
    39
    Thanked 201 Times in 197 Posts

    progress made - 1 final thing to resolve

    Hi,

    Never mind.. I'm officially stoopid. I got it in the end.

    bazz
    Last edited by bazz; 08-20-2009 at 03:15 PM.
    "The day you stop learning is the day you become obsolete"! - my late Dad.

    Why do some people say "I don't know for sure"? If they don't know for sure then, they don't know!
    Useful MySQL resource
    Useful MySQL link

  • #9
    New Coder
    Join Date
    Aug 2009
    Location
    in front of the keyboard
    Posts
    17
    Thanks
    1
    Thanked 1 Time in 1 Post
    Quote Originally Posted by bazz View Post
    This is my most recent way and it is easier to follow the dumped output and may associate sufficiently well.
    Sorry to mingle. Don't know if it's still necessary, but I think you're using the hashes here quite inefficiently. Normally, if you can avoid extra levels, you should. Hashes in Perl are not that time-economic.

    I don't really get why you have a level $terms_abbr and a level $terms. I would get rid of the level $terms and create a second hash to link the $terms_abbr and the $terms. The same I'd do for the levels "age_data" and $age_group.

    Something like this :
    Code:
    $terms_abbr_hash{$terms_abbr}{$full}=$terms;
    $terms_abbr_hash{$terms_abbr}{'age data'}=$age_group;
    
    $new_tariffs_hash{$live_product_id}{$terms_abbr}=$price;
    $new_tariffs_hash{$live_product_id}{'tariff_start_date'}=$tariff_start_date;
    $new_tariffs_hash{$live_product_id}{'tariff_end_date'}=$tariff_end_date;
    $new_tariffs_hash{$live_product_id}{'nights_on_first_tariff'} = $nights_on_first_tariff;
    $new_tariffs_hash{$live_product_id}{'nights_on_second_tariff'} = $nights_on_second_tariff;
    I think this is a bit more economic on the memory too. If you build your hash as deep as you do, you actually duplicate the same information numerous times : the term-abbreviations are always related to the same age group and the same terms, no?

    Hope this makes sense. Feel free to disagree, I'm no expert.

  • Users who have thanked Jolle for this post:

    bazz (08-21-2009)

  • #10
    Master Coder
    Join Date
    Apr 2003
    Location
    in my house
    Posts
    5,211
    Thanks
    39
    Thanked 201 Times in 197 Posts
    food for thought, certainly.

    I shall mull over your suggestion and try to make the hashes run more efficiently.

    the term-abbreviations are always related to the same age group and the same terms, no?
    not quite. the terms relate to the price irrespective of the age group. they are effectiently, price clarification. eg pppn = per person per night.

    But I get the principle of your post and I'll try to work with it for a better outcome.

    Finally; finally, hashes are becoming clearer to me. what is it they say - necessity is the mother of all invention? On further thought maybe it's, 'mother is the inventor of all necessity'

    bazz
    "The day you stop learning is the day you become obsolete"! - my late Dad.

    Why do some people say "I don't know for sure"? If they don't know for sure then, they don't know!
    Useful MySQL resource
    Useful MySQL link

  • #11
    New Coder
    Join Date
    Aug 2009
    Location
    in front of the keyboard
    Posts
    17
    Thanks
    1
    Thanked 1 Time in 1 Post
    Quote Originally Posted by bazz View Post
    food for thought, certainly.
    you're welcome. Enjoy the lunch
    not quite. the terms relate to the price irrespective of the age group. they are effectiently, price clarification. eg pppn = per person per night.
    I see. I just assumed it as you didn't seem to have a term_abbreviation that is used in two age groups.

    Good luck with it.

  • #12
    Master Coder
    Join Date
    Apr 2003
    Location
    in my house
    Posts
    5,211
    Thanks
    39
    Thanked 201 Times in 197 Posts
    I'll try the new approach and do some benchmarking to see the efficiency differences.

    bazz
    "The day you stop learning is the day you become obsolete"! - my late Dad.

    Why do some people say "I don't know for sure"? If they don't know for sure then, they don't know!
    Useful MySQL resource
    Useful MySQL link

  • #13
    New Coder
    Join Date
    Aug 2009
    Location
    in front of the keyboard
    Posts
    17
    Thanks
    1
    Thanked 1 Time in 1 Post
    Quote Originally Posted by bazz View Post
    I'll try the new approach and do some benchmarking to see the efficiency differences.

    bazz
    On second thought, it might be easier if you adjust a bit, otherwise it gets complicated to extract all prices. Some code to illustrate what I mean :

    Code:
    #!/usr/bin/perl -w
    use strict; # yeah, I'm feeling kinky
    
    my (%terms_abbr_hash, %new_tariffs_hash);
    
    # the data
    my @terms_abbr_array = (
        ["pppns", "Per Person Per night Sharing","Adult"],
        ["prpn", "Per Room Per Night","Adult"],
        ["sopn", "Single Occupancy Per Night","Adult"],
        ["pacpn", "Per Accompanied Child Per Night","Up to 12 yrs"]
    );
    
    # the loop to fill your hash
    foreach (@terms_abbr_array){
        my ($terms_abbr,$terms,$age_group)=@{$_}; # unref array, keep local
        # fill up the hash
        $terms_abbr_hash{$terms_abbr}{full}=$terms;
        $terms_abbr_hash{$terms_abbr}{agedata}=$age_group;
    }
    
    # let's make some data. first the product specifications
    my @new_tariffs_array = (
        [84,"2010-03-31","2009-10-01",0,5],
        [85,"2009-09-30","2009-08-01",3,2],
        [83,"2009-09-30","2009-08-01",3,2]
    );
    # let's fill the hash
    foreach (@new_tariffs_array){
        my ($live_product_id,$tariff_start_date,$tariff_end_date,
            $nights_on_first_tariff,$nights_on_second_tariff)=@{$_};
    
        $new_tariffs_hash{$live_product_id}{tariff_start_date}=$tariff_start_date;
        $new_tariffs_hash{$live_product_id}{tariff_end_date}=$tariff_end_date;
        $new_tariffs_hash{$live_product_id}{nights_on_first_tariff} = $nights_on_first_tariff;
        $new_tariffs_hash{$live_product_id}{nights_on_second_tariff} = $nights_on_second_tariff;
    }
    # OK, lets add some prices
    my @new_tariffs_prices =(
        [84,"pppns",32.50],
        [84,"prpn",65.00],
        [84,"sopn",45.00],
        [85,"pppns",32.50],
        [85,"prpn",65.00],
        [85,"sopn",45.00],
        [83,"pacpn",25.44],
        [83,"pppns",30.00],
        [83,"prpn",60.00],
        [83,"sopn",40.00],
    
    );
    # let's fill the hash
    foreach (@new_tariffs_prices){
        my ($live_product_id,$terms_abbr,$price)=@{$_};
        $new_tariffs_hash{$live_product_id}{prices}{$terms_abbr}=$price;
    }
    
    # And let's print everything out in a readable format :
    foreach my $id (keys %new_tariffs_hash){
        print qq/
            Product $id :
            Tariff start date       : $new_tariffs_hash{$id}{tariff_start_date}
            Tariff end date         : $new_tariffs_hash{$id}{tariff_end_date}
            Night on first tariff   : $new_tariffs_hash{$id}{nights_on_first_tariff}
            Nights on second tariff : $new_tariffs_hash{$id}{nights_on_second_tariff}
            Prices :
        /;
        foreach my $term_abbr (keys %{$new_tariffs_hash{$id}{prices}}){
            print qq/
                $terms_abbr_hash{$term_abbr}{full} : $new_tariffs_hash{$id}{prices}{$term_abbr}
                ageclass : $terms_abbr_hash{$term_abbr}{agedata}
    /;
        }
    }
    
    # Let's try to display all prices for a certain product and a certain age group :
    while (1){ # play with an infinite loop a bit
        print "\nGive a product or type C to cancel :";
        my $prodid = <STDIN>;
        chomp $prodid;
        print "\nGive an age group : Adult or Minor :"
            unless $prodid =~/C/i and last;
        my $agegroup = <STDIN>;
        if ($agegroup =~ /adult/i){
            $agegroup = "Adult";
        } elsif ($agegroup =~ /minor/i){
            $agegroup = "Up to 12 yrs";
        } else {
            print "\n Age group is not valid.\n" and next;
        }
        # let's find what we need
        my %prices = %{$new_tariffs_hash{$prodid}{prices}} or
            (print "\nProduct not found\n" and next);
        foreach (keys %prices) {
            print "$terms_abbr_hash{$_}{full} : $prices{$_}\n"
                unless ($terms_abbr_hash{$_}{agedata} ne $agegroup) and next;
        }
    }
    That's at least how I would do it. I think in my own thread, there is an example of that in one of the scripts too.

    Let me know the results of the benchmarking, I'm quite curious in fact. I'm not an experienced programmer, so I might be way off here.
    Last edited by Jolle; 08-21-2009 at 05:27 PM.

  • #14
    New Coder
    Join Date
    Aug 2009
    Location
    in front of the keyboard
    Posts
    17
    Thanks
    1
    Thanked 1 Time in 1 Post
    Just to make sure, my last code would create hashes equivalently to :
    Code:
    $terms_abbr_hash{$terms_abbr}{'full'}=$terms;
    $terms_abbr_hash{$terms_abbr}{'age data'}=$age_group;
    
    $new_tariffs_hash{$live_product_id}{'prices'}{$terms_abbr}=$price;
    $new_tariffs_hash{$live_product_id}{'tariff_start_date'}=$tariff_start_date;
    $new_tariffs_hash{$live_product_id}{'tariff_end_date'}=$tariff_end_date;
    $new_tariffs_hash{$live_product_id}{'nights_on_first_tariff'} = $nights_on_first_tariff;
    $new_tariffs_hash{$live_product_id}{'nights_on_second_tariff'} = $nights_on_second_tariff;
    Made a mistake in my first post.
    Last edited by Jolle; 08-21-2009 at 05:33 PM. Reason: duh, can't type right today

  • #15
    Master Coder
    Join Date
    Apr 2003
    Location
    in my house
    Posts
    5,211
    Thanks
    39
    Thanked 201 Times in 197 Posts
    Suddenly, I feel inadequate.

    I'll read over that again later and see if I can incorporate it with a bit of modification.

    Thank you

    bazz
    "The day you stop learning is the day you become obsolete"! - my late Dad.

    Why do some people say "I don't know for sure"? If they don't know for sure then, they don't know!
    Useful MySQL resource
    Useful MySQL link


  •  
    Page 1 of 2 12 LastLast

    Posting Permissions

    • You may not post new threads
    • You may not post replies
    • You may not post attachments
    • You may not edit your posts
    •