CGI/Perl Guide | Learning Center | Forums | Advertise | Login Site Search: in Perl Guide PerlGuru Forums Learning Ctr

Home: Perl Programming Help: Beginner:
Perl to print previous and current value

eminempark
Novice

May 21, 2013, 8:11 PM

Post #1 of 10 (1630 views)
 Perl to print previous and current value Can't Post
How if i want to put formula of (cur_val - 2 * pre_val + pre_pre_val) >= 0.25 into the perl? For example, I have a number.txt consists of
 Code
`1 0.1 2 0.4 3 0.9 4 0.6 5 0.5 6 0.6 7 0.9 8 0.4 9 0.1 10 0.0`
The expected process is
 Code
`1 0.1 #by default it will print out the first two value 2 0.4 #by default it will print out the first two value 3 0.9 # ABS(0.9 - 2 * 0.4 (y of 2)+ 0.1 (y of 1)) = 0.2, 0.2 < 0.25, thus, will not printed out 4 0.6 # ABS(0.6 - 2 * 0.4 (y of 2)+ 0.1 (y of 1)) = 0.1, 0.1 < 0.25, thus, will not printed out 5 0.5 # ABS(0.5 - 2 * 0.4 (y of 2)+ 0.1 (y of 1)) = 0.2, 0.2 < 0.25, thus, will not printed out 6 0.6 # ABS(0.6 - 2 * 0.4 (y of 2)+ 0.1 (y of 1)) = 0.1, 0.1 < 0.25, thus, will not printed out 7 0.9 # ABS(0.9 - 2 * 0.4 (y of 2)+ 0.1 (y of 1)) = 0.2, 0.2 < 0.25, thus, will not printed out But because the x=8 is printed out, x=7 will be printed out as well. 8 0.4 # ABS(0.4 - 2 * 0.4 (y of 2)+ 0.1 (y of 1)) = 0.3, 0.3 >= 0.25, thus, will printed out 9 0.1 # ABS(0.1 - 2 * 0.4 (y of 8)+ 0.9 (y of 7)) = 0.2, 0.2 < 0.25, thus, will not printed out 10 0.0 # ABS(0.0 - 2 * 0.4 (y of 8)+ 0.9 (y of 7)) = 0.1, 0.1 < 0.25, thus, will not printed out`
Thus, the output will be
 Code
`1 0.1 2 0.4 7 0.9 8 0.4`
So far, my perl script is:
 Code
`#! /usr/bin/perl -w # # compare.pl # # Usage: compare.pl number.txt # # use strict;  my \$pre_value = 14091989; my \$pre_pre_value = 1; while(<>){   my( \$ID, \$cur_value) = split;   if( abs(\$cur_value-2*\$pre_value+\$pre_pre_value) >= 0.25 ){     print \$_;     \$pre_pre_value = \$pre_value;     \$pre_value = \$cur_value;   }   else   {     \$pre_value = \$pre_value;     \$pre_pre_value = \$pre_pre_value;   } }`

Laurent_R
Veteran / Moderator

May 22, 2013, 4:48 AM

Post #2 of 10 (1621 views)
 Re: [eminempark] Perl to print previous and current value [In reply to] Can't Post
Hmm, the code in your else branch isn't very useful, is it?

From your description of the problem, I would think that the assignments:

 Code
`\$pre_pre_value = \$pre_value;  \$pre_value = \$cur_value;`

should be done outside of the if clause, since you presumably want to do that in all cases.

So I would code it this way:

 Code
`use strict;   my \$pre_value = 14091989;  my \$pre_pre_value = 1;  while(<DATA>){    	my( \$ID, \$cur_value) = split;    	if( abs(\$cur_value - 2  *\$pre_value + \$pre_pre_value) >= 0.25 ){ 		print \$_;      	}  	\$pre_pre_value = \$pre_value;      	\$pre_value = \$cur_value; } __DATA__ 1 0.1 2 0.4 3 0.9 4 0.6 5 0.5 6 0.6 7 0.9 8 0.4 9 0.1 10 0.0`

This gives me this result:
 Code
`\$ perl  prevalue.pl 1 0.1 2 0.4 4 0.6 8 0.4`
which seems to be correct to me (it I understood correctly what you are trying to do).

eminempark
Novice

May 23, 2013, 12:22 AM

Post #3 of 10 (1602 views)
 Re: [Laurent_R] Perl to print previous and current value [In reply to] Can't Post
Hm... Based on your result, sorry to say that it is wrong.
The process is:
 Code
`1 0.1 #by default it will print out the first two value  2 0.4 #by default it will print out the first two value  3 0.9 # ABS(0.9 - 2 * 0.4 (y of 2)+ 0.1 (y of 1)) = 0.2, 0.2 < 0.25, thus, will not printed out  4 0.6 # ABS(0.6 - 2 * 0.4 (y of 2)+ 0.1 (y of 1)) = 0.1, 0.1 < 0.25, thus, will not printed out  5 0.5 # ABS(0.5 - 2 * 0.4 (y of 2)+ 0.1 (y of 1)) = 0.2, 0.2 < 0.25, thus, will not printed out  6 0.6 # ABS(0.6 - 2 * 0.4 (y of 2)+ 0.1 (y of 1)) = 0.1, 0.1 < 0.25, thus, will not printed out  7 0.9 # ABS(0.9 - 2 * 0.4 (y of 2)+ 0.1 (y of 1)) = 0.2, 0.2 < 0.25, thus, will not printed out But because the x=8 is printed out, x=7 will be printed out as well.  8 0.4 # ABS(0.4 - 2 * 0.4 (y of 2)+ 0.1 (y of 1)) = 0.3, 0.3 >= 0.25, thus, will printed out  9 0.1 # ABS(0.1 - 2 * 0.4 (y of 8)+ 0.9 (y of 7)) = 0.2, 0.2 < 0.25, thus, will not printed out  10 0.0 # ABS(0.0 - 2 * 0.4 (y of 8)+ 0.9 (y of 7)) = 0.1, 0.1 < 0.25, thus, will not printed out`
Thus, the result should be:
 Code
`1 0.1  2 0.4  7 0.9  8 0.4`

Laurent_R
Veteran / Moderator

May 23, 2013, 4:55 AM

Post #4 of 10 (1596 views)
 Re: [eminempark] Perl to print previous and current value [In reply to] Can't Post
Let's see. The differences between my results and those that you show are on lines 2 and 7.

Prev value: 14091989
1 0.1
2 0.4

Line 2: 0.4 - 2 * 0.1 + 14091989 = 14091989,2, larger than 2.5, should be printed.

5 0.5
6 0.6
7 0.9

Line 7: 0.9 - 2 * 0.6 + 1 * 05 = 2, smaller than 2.5, should not be printed.

My results are consistent with the rules you have explained, yours are not.

Or you have to explain you rules better.

BillKSmith
Veteran

May 23, 2013, 12:20 PM

Post #5 of 10 (1583 views)
 Re: [Laurent_R] Perl to print previous and current value [In reply to] Can't Post
Laurent,
I initially got the same result as you. After the OP declared that wrong, I went back to his code. The difference is that he only updates the history if he does the print. I now believe that is intentional. That would be correct, but he now has an additional requirement which looks like a mere comment.

 Quote
But because the x=8 is printed out, x=7 will be printed out as well

After line 8 is processed, but before it is printed, he has to print line 7 and revise the history so that line 9 will get its pre from line 8 and its pre_pre from line 7 (not 2).

I assume that this processing is needed every time a line is printed, and its immediate successor was not. It would not make sense to consider this requirement recursive.

This will take some deep thought.
Good Luck,
Bill

Laurent_R
Veteran / Moderator

May 23, 2013, 3:18 PM

Post #6 of 10 (1577 views)
 Re: [BillKSmith] Perl to print previous and current value [In reply to] Can't Post
Yes, Bill, yes, of course, you are right, I fully understand that what I provided is not what the OP really wanted. But it is my best understanding of the way the OP described the problem. And the code provided does in my opinion what the OP requested.

From the OP's own recognition, his or her code does not do what he or she wants. Therefore, you or I can't rely on the code provided by the OP to guess what he or she wants.

The reason I challenged the OP's opinion that my solution was wrong is certainly not that I wanted absolutely to defend my code (I frankly don't care), the OP hopefully knows better that you or I what he or she wants. The reason I did it is simply to prompt the OP to give better specifications of the requirement.

The table provided by the OP is only confusing to my eyes: for every single line, the second member of the equation if "-0.4 * 2". Even though I have an idea why, the point is that an example is never a substitute for a real explanation of the rule.

I have an idea of what the OP really wants, but I want him or her to state it clearly and to explain precisely the rules of the game.

It is probably not very complicated to obtain the desired result, but I will not commit any more effort on this until the need is clearly specified. Once we know really what the OP wants, I'm willing to take it up again.

To the OP: don't take this as an attack, it is not that, I am just trying to say that you need to make clear what you really want. Quite possibly, if you do the exercise seriously, you will find the solution by yourself. Believe my long experience: dfefining clearly what you need is the key to success. The programming itself is a secondary matter. I have been using probably more than 20 programming languages in my life, of which at least a dozen for real life professional problems, the issue of figuring out exactly what you need is far more important that knowing whether it will be programmed in Fortran, Lisp, C, PHP or Perl (or whatever).

BillKSmith
Veteran

May 23, 2013, 9:39 PM

Post #7 of 10 (1571 views)
 Re: [Laurent_R] Perl to print previous and current value [In reply to] Can't Post
Laurent,

The table provided by the OP is certainly confusing. But, once I deciphered it, I considered it a reasonably complete description of the problem. My previous post was not based on any guess. It is fully consistent with my understanding of the table. I had hoped that with that much clarification, we could both work on the real problem.

Please reconsider your response. Look at the table once more with the idea that it does contain the spec that you want. The first six lines are consistent with the OP's code. The seventh is different because of an additional requirement explained in the comment.

Note:
Pre and Pre_Pre do not refer the previous physical lines, but to the two previously printed lines.

x and y refer to the integer and real parts of a line respectively

You complained about all the 0.4's in the PRE colulmn. In rows 3 through 8, the 0.4 is the y-value from row 2 (the previously printed row.) The OP documents this with the notation '(y of 2)'
Row 8 is printed. The 0.4 in rows 9 and 10 is the y-value from row 8 which has become the previous printed row. It is an unfortunate coincidence that those y-values are the same.

The PrePre column is more complicated. Rows 2 through 8 contain the y-value from row 1 (the second previously printed row.) Without the new requirement to print row 7, rows 9 and 10 would both use the y-value from row 2. Now that row 7 is printed, they must get the y-value from it.
Good Luck,
Bill

Laurent_R
Veteran / Moderator

May 24, 2013, 1:26 AM

Post #8 of 10 (1566 views)
 Re: [BillKSmith] Perl to print previous and current value [In reply to] Can't Post
Alright, Bill, you've convinced me. Here we go.

I still think that the OP should learn to express requirements more precisely in plain language, but I can't resist to the pleasure of problem solving.

This is my new version. I am not entirely sure how exactly \$pre_value and \$pre-pre_value should be modified when one line is printed because the next one matches the condition, I have implemented what looks the most plausible to me.

 Code
`use strict;   my \$pre_value = 14091989;  my \$pre_pre_value = 1;  my \$previous_line =""; while(<DATA>){    	my( \$ID, \$cur_value) = split;    	if( abs(\$cur_value - 2  *\$pre_value + \$pre_pre_value) >= 0.25 ){ 		if (\$previous_line) { 			print \$previous_line; 			\$pre_pre_value = \$pre_value; # this line is useless but keeping it conveys the logic better 			\$pre_value = (split / /, \$previous_line)[1]; 		} 		print \$_; 		\$pre_pre_value = \$pre_value;      		\$pre_value = \$cur_value; 		\$previous_line = ""; 	} else { 		\$previous_line = \$_; 	} } __DATA__ 1 0.1 2 0.4 3 0.9 4 0.6 5 0.5 6 0.6 7 0.9 8 0.4 9 0.1 10 0.0`

And the output is:

 Code
`\$ perl prevalue.pl 1 0.1 2 0.4 7 0.9 8 0.4`

BillKSmith
Veteran

May 24, 2013, 6:16 AM

Post #9 of 10 (1561 views)
 Re: [Laurent_R] Perl to print previous and current value [In reply to] Can't Post
Thanks Laurent, that is exactly what I wanted. I hope the OP can say the same thing.

I found your solution this morning before I had a chance to work on it more myself. Everything I had considered so far was much more complex. I had not thought of extracting the special previous value from the previous line.
Good Luck,
Bill

eminempark
Novice

May 26, 2013, 7:46 PM

Post #10 of 10 (1538 views)
 Re: [Laurent_R] Perl to print previous and current value [In reply to] Can't Post
Exactly what I need. Thank you Laurent_R and Bill.

 Announcements     PerlGuru Announcements Perl Programming Help     Frequently Asked Questions     Beginner     Intermediate     Advanced     Regular Expressions     mod_perl     DBI     Win32 Programming Help Fun With Perl     Perl Quizzes - Learn Perl the Fun Way     Perl Golf     Perl Poetry Need a Custom or Prewritten Perl Program?     I need a program that...     I Need a Programmer for Freelance Work     Throw Down The Gauntlet General Discussions     General Questions     Feedback     Tutorial/Article Suggestions for The Learning Cent     Internet Security Other Programming Languages     Javascript     PHP

 Search this forum this category all forums for All words Any words Whole Phrase (options) Powered by Gossamer Forum v.1.2.0