"N, Guruguhan (GEAE, Foreign National, EACOE)" wrote: > Hi All, > I have written a perl code for filtering data contained in a file > ($input_file_name) based on the filter expression($expr). While doing this, I face > some problems. When I hard code the arrays @data and @col
> ( in red color) Please don't do that. HTML is filtered out of postings to this list, so anything that relies on markup will be lost. > in the code, I am getting the results. But the moment I get the arrays @col and > @data based on the user input file ($input_file_name) inside the "if" loop, there is > no filter. The reason is @data array inside the "if" loop (red colored) when > accessed outside has only one value and that doesn't satisfy the filter expression. > Then I changed it look like the one given in blue color. Now I don't know how should > I modify > 1. the sub routine sub filterdata > 2. my @result array > 3. print join function > All the three are highlighted in blue color. > > Can some one please suggest me what changes I have to do, so that I can get the > results? Any help in this regard is solicited. > > > #! /usr/bin/perl -w > use strict; #- matter of style Yes--do use strict, and no--it is not just amatter of style. > use warnings; #- and again Likewise as above. Not just a matter of style, but a critical necessity if you wish to learn how to write solid, orbust programs in Perl. > > > my (@col,@data,$input_file_name,@temp,$header,$data_line,$i); Don't do this. Declaring all your variables in an unrelated lump defeats the purpose of using strict. Declare your variables as close as possible to the place where they are initialized. > > $input_file_name= "MC_data.dat"; > > if (-s $input_file_name ) { > open(INPUT, $input_file_name) || die "Cannot open: \nReason: $!\n"; Don't indent here. Indentation should mark execution blocks. The flow of execution does not change here, so all lines within this if statement should be vertically aligned. > > @temp = <INPUT> ; Here is your immediate problem. The line above puts the first line of the file into the first element of @temp. If you must dump all your data into an array, then you will have to put the input operation into list context by enclosing it in parentheses: @temp = (<INPUT>); > > chomp @temp; > $header = shift(@temp); > $header =~ s/^\s+(.*)/$1/; #Remove the leading white spaces > @col = split /\s+/, $header; > > foreach $i ( 0 .. $#temp ) { Do indent here. Everything within this for loop should be indented by however many spaces you are using as standard indentation. Indent after the opening brace. Unindent the line that holds the closing brace. perldoc perlstyle > > $data_line = $temp[$i]; > $data_line =~ s/^\s+(.*)/$1/; #Remove the leading white spaces > @data = split /\s+/, $data_line; @data, huh? Is there anything you would be processing that is not data?!? Use variable names that mean something. > > $data[$i] = split /\s+/, $data_line; > } > } > > @col = qw (RUN a1 a2 a3 weight sig1 sig2 sig3); > > @data=( > [qw( 1 0.200000 0.200000 0.200000 0.765685 75881.9 > 29289.3 -46592.6)], Why qw? These all look like numbers to me. Much more clear to write: [1, 0.2, 0.2, 0.2, 0.765685, 75881.9, 29289.3, -46592.6], Unless there is some very good reason why these *must* be stored as character strings rather than numbers. > > [qw( 2 0.200345 0.200000 0.200345 0.966661 75766.0 > 29268.4 -46497.6)], > [qw( 3 0.200000 0.200345 0.200000 0.766030 75867.1 > 29259.8 -46607.4)], > [qw( 4 0.359575 0.253987 0.359575 1.271019 43898.7 > 19675.6 -24223.1)], > [qw( 5 0.359921 0.253987 0.359921 1.271995 43861.3 > 19666.1 -24195.2)] > ); > > map What array is being assigned the return value of map? If you are not trying to return an array, map is not an appropriate tool. You should probably be using a for loop to iterate through the array. > { my $i=$_; What are you doing with $r? Where are you using it? Please don't assign things to variables that then vanish into thin air. > no strict 'refs'; *{"filter::$col[$i]"} = sub{$_->[$i]} } This probably does something. It's really not worth it to try to figure out what, though. Do you understand what it is doing? If you do not, then don't use it. Hint: if you have to turn strict off, you probably are doing something that will be undependable. Calling well-constructed subroutines is much more simple and clear than this filterdata($validation_function_ref, @lines_to_be_tested); > > 0..$#col; > > sub filterdata > { > my $cref=shift; > grep &$cref,@_ > } > > sub filterspec > { > my $e = shift; > map{ $e =~ s/\b$_\b/filter::$_()/g } @col; > eval "sub{ $e }" > } > > my $expr = "weight < 1.2 && sig1 > 75800"; > > my $filter_handler = filterspec( $expr ) or die $@; > > my @result = filterdata ($filter_handler,@data); > > print join("$/",map{join(" ",@$_)[EMAIL PROTECTED]).$/; > Thanks > Regards > Guruguhan > EACoE, India. Overall, I would recommend that you back up a few paces, and work on one coding concept at a time. You seem to have trouble even with one-dimensional arrays. You should do more exercises with simple arrays, and get a better understanding of the way they work, before you try to tackle more complicated structures. Remember--if it is hard for a human to make sense of, it is even less likely that a compiler will understand it. Write for clarity. Joseph -- To unsubscribe, e-mail: [EMAIL PROTECTED] For additional commands, e-mail: [EMAIL PROTECTED] <http://learn.perl.org/> <http://learn.perl.org/first-response>