http://www.perlmonks.org?node_id=1193607


in reply to Delay in Writing the data to Text file

This is largely consistent with haukex's response, but more verbose. Note that your posted script does not pass strict as written, and so does not run as posted. It's considered poor form to post code that doesn't compile; it's far better to post ugly code that behaves like what is on your system.

As soon as your challenge is "my code is too slow," your first thought should be to profile your code. I'm a fan of Devel::NYTProf, but there are alternatives. If you ran a profiler, you'd likely see that the while loop in getCount takes up most of your time, for reasons haukex pointed out. In order to speed things up, you want to only read in each file once. There are two basic options for doing this:

  1. Prepocess/Store all the relevant data from $MobileServiceLog in memory, and loop over $MSMLog
  2. Prepocess/Store all the relevant data from $MSMLog in memory, and loop over $MobileServiceLog
You'd generally pick one or the other based upon which one takes more memory. Assuming both files are small, the minimal way of making that happen might be
print("\nnumber of occurance is $count\n"); #!/usr/bin/perl use 5.010; use strict; use warnings; #Open MSM Log in read Mode open(my $MSMLog, '<','MSMLogs.txt'); #Create Audit txt file in write mode open(my $Audit, '>','br.1'); print("Task Started.........\n"); #iterate each word to identify the logs while (my $row = <$MSMLog>) { chomp $row; getCount($row); } { my @rows; sub getCount { #Open MobileService.log file in read mode if (not @rows) { open(my $MobileServiceLog, '<','one.txt'); @rows = <$MobileServiceLog>; close $MobileServiceLog; } my @StaticLog = @_; my $count = 0; #print ("\nvalue in MSM Static is ------ $StaticLog[0]\n"); for my $row (@rows) { my @actualWord = split /;/, $row; my $MobileService = $actualWord[7]; #print ("value in MobileService is ------ $MobileService\n"); if ($MobileService =~ /$StaticLog[0]/) { $count += 1; } } $_=1 print ($Audit "\n$StaticLog[0] occurance is ------- \t$count\n"); print("\nnumber of occurance is $count\n"); } } print ($Audit "Task Completed"); print ("Task Completed"); close $MSMLog; close $Audit;
where I've used a block to keep @rows reasonably scoped. Note that this still has many inherited flaws, such as not passing strict and not testing your opens for success. There are also a number of other potential optimizations, particularly depending on what you intend by if ($MobileService =~ /$StaticLog[0]/) {, such as using index or hashes.

#11929 First ask yourself `How would I do this without a computer?' Then have the computer do it the same way.