For anyone still following this thread, I think the point is now rather
moot.

Using Perl, I tried variations of fork & wait with no noticeable speed
performance.

Determined to try threads, I busted out the Ruby Pick-Axe book and created a
threaded version.  Still no performance improvement.

It now seems clear to me that, whatever I may come up with on the client
side the Oracle Server is going to handle its own way regardless.

Looks like nothing is faster than ye old "sqlplus blah/blah@music_teleblah <
sqlfile.txt".

Sigh...

Thanks for all the help & suggestions.  At least I know more about shared
memory than I ever did before. :)

Regards,

Dan

On Fri, 25 May 2001 08:37:37 -0500, Mr. Sunray said:

> Hi all,
>  
>  Perl 5.6 on bughat 6.2, using DBI 1.14, DBD-Oracle 1.06.
>  
>  Ok - I thought I'd try and optimize a series of sql SELECT statements by
>  
>  forking each one and storing the results in a shared memory object.
>  
>  Here's the code - I'm reading a series of sql select statements from a
>  file, fork'ing a child for each one, executing the 'fetch' within the
>  child and trying to store the results in an array for later retrieval.
>  
>  The problem seems to be with the shared memory objects.  Either the
>  array of results grows each time I run the program or else I get "Can't
>  use an undefined value as an ARRAY reference at
>  /usr/local/lib/perl5/site_perl/5.6.0/IPC/Shareable.pm line 446, <GEN1>
>  chunk whatever".
>  
>  Now, I've been told that part of the problem (at least) is that I'm
>  trying
>  to store references, which probably won't work (though it seems to
>  work sometimes).
>  
>  I guess my big question is how can I use fork to speed up my queries
>  *and*
>  store the results in the parent (without using a text file)?  Should I
>  be
>  looking at threads instead?  Is there a *standard idiom*?
>  
>  Thanks in advance for any help.
>  
>  WARNING - be prepared to use 'ipcs' and 'ipcrm' if you want to play with
>  
>  this script!  You may have stray memory objects floating around
>  afterwards.
>  
>  Be sure to run this/your program at least twice to make sure your shared
>  
>  memory objects aren't "collecting".
>  
>  #!/usr/local/bin/perl -w
>  
>  use strict;
>  use DBI;
>  use DBD::Oracle;
>  use IPC::Shareable;
>  use IO::File;
>  use POSIX qw(WNOHANG);
>  
>  use constant DB => 'myDB';
>  use constant USER => 'user';
>  use constant PASSWD => 'passwd';
>  use constant DRIVER => 'Oracle';
>  
>  #+++++++++++++++++++++++++++++++++++++++++++++
>  # File contains 4 sql SELECT statements.
>  # Use "select sysdate from dual" if you like, so long as it works.
>  #+++++++++++++++++++++++++++++++++++++++++++++
>  use constant SQLFILE => 'file.sql';
>  
>  # Child handler
>  $SIG{CHLD} = \&reapChild;
>  
>  my($dbh, $sth, @results, @allRecords);
>  my $if = IO::File->new(SQLFILE) or die "Couldn't open file: $!\n";
>  
>  #+++++++++++++++++++++++++++++++++++++++++++++++++
>  # I am not entirely sure what the proper settings for these should be.
>  # I've tried various combinations with no (or bad) luck.
>  #+++++++++++++++++++++++++++++++++++++++++++++++++
>  my $glue = 'data';
>  my %options = (create => 'yes', exclusive => 0, destroy=>1)
>  tie @allRecords, 'IPC::Shareable', $glue, { %options } or die "Tie
>  failed: $!\n";
>  
>  $/ = "";  # We're going to read each 'select' statement as an input
>  record
>  while(my $query = <$if>){
>     chomp($query);
>  
>     my $child = fork();
>     die "Can't fork: $!\n" unless defined $child;
>  
>     if($child == 0){
>  
>          # Not sure if I need 'InactiveDestroy' here or not
>          $dbh = DBI->connect(DB,USER,PASSWD,DRIVER,
>              {RaiseError=>1,PrintError=>1,InactiveDestroy=>1}
>          );
>  
>          $sth = $dbh->prepare($query);
>          $sth->execute();
>          while( my $hash_ref = $sth->fetchrow_hashref() ){
>              push(@results, $hash_ref);
>          }
>  
>          #+++++++++++++++++++++++++++++++++++++++++++++
>          # '@allRecords' should contain a reference to an array of hash
>          # reference for each select statement (thus, four total).
>          #+++++++++++++++++++++++++++++++++++++++++++++
>          push(@allRecords, \@results);
>  
>          $sth->finish();
>          $dbh->disconnect();
>          exit 0;
>      }
>  }
>  
>  close($if) or die "Unable to close input file: $!\n";
>  
>  #+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
>  # I expect to see four array references here.  When I try this, I either
>  
>  # get "Can't use undefined value as an array reference" warnings
>  # from the 'Shareable.pm' module or the list keeps growing and growing
>  # each time I run the program.  What do I need to do?
>  #+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
>  foreach my $ref(@allRecords){
>      print "Ref is: $ref\n";
>  }
>  
>  sub reapChild{ do {} while waitpid(-1, WNOHANG) > 0 }
>  
>  
>  
>  
>  
>  

-- 
Michael Wray
Network Administrator
FamilyConnect, Inc.

Reply via email to