[lnkForumImage]
TotalShareware - Download Free Software

Confronta i prezzi di migliaia di prodotti.
Asp Forum
 Home | Login | Register | Search 


 

Forums >

comp.lang.ruby

embedding if statements in upto function.(newbie question

Michael Sc

2/12/2007 11:05:00 AM

Thank you to everyone for all of your help.
I was trying to use upto to go through an array of arrays while using if
statments. Could anyone enlighten me on what I am doing wrong with the
if statements?
I am sure it is something easy.

I tried this:
0.upto( a.size-2 ) {|i|
if (a[i][2]==a[i+1][2] and a[i][0]==a[i+1][0]) then
print { (a[i+1][3] - a[i][3]) / a[i][3] * 100 } /n
else print 0
end}

Thanks again for all of the help.
Michael

--
Posted via http://www.ruby-....

6 Answers

Brian Candler

2/12/2007 11:54:00 AM

0

On Mon, Feb 12, 2007 at 08:05:01PM +0900, Michael Sc wrote:
> Thank you to everyone for all of your help.
> I was trying to use upto to go through an array of arrays while using if
> statments. Could anyone enlighten me on what I am doing wrong with the
> if statements?
> I am sure it is something easy.
>
> I tried this:
> 0.upto( a.size-2 ) {|i|
> if (a[i][2]==a[i+1][2] and a[i][0]==a[i+1][0]) then
> print { (a[i+1][3] - a[i][3]) / a[i][3] * 100 } /n
> else print 0
> end}

Why don't you give some sample data, and show what happens when you run it.
Preferably make a small, standalone program which demonstrates the problem.
Do you get an exception raised? A wrong result?

Looking at the above, the fact that you have used curly brackets in the
'print' statement certainly won't help... this creates a code block and will
give you a confusing error like this:

irb(main):003:0> print { 4 + 5 } / 3
nilNoMethodError: undefined method `/' for nil:NilClass
from (irb):3
from :0

This is equivalent to:

print( { 4+5 } ) / 3
^ ^ ^
| | |
| | value returned by
| | print() is nil
| |
| a code block
| which is not used
|
no arguments
to print

BTW you probably want to use puts rather than print, so your numbers are on
separate lines; or at least print a space between them.

Your above code does also highlight a skeleton in Ruby's closet: note that

puts (4+5)/3

puts(4+5)/3

are two different constructs, even though they differ only by one space.
They are equivalent to, respectively,

puts( (4+5)/3 ) # probably what you want

( puts(4+5) ) / 3 # prints 9, tries to divide nil by 3

B.

Michael Sc

2/12/2007 12:50:00 PM

0

Thanks Brian, I appreciate the help.


I changed the code and ran it again.
0.upto( a.size-2 ) {|i|
if (a[i][2]==a[i+1][2] and a[i][0]==a[i+1][0]) then
puts ( (a[i+1][3] - a[i][3]) / a[i][3] * 100 )
else puts 0
end}
With this I get an error on the 3rd line of undefined method(-) for ".08
#(the first number)#":String(NoMethodError)Print was able to do the
calculation without the if statements. I think I misunderstood how
output in FasterCSV processes files. basically, I sorted a csv file and
I was trying to do some simple math on that file.

Basically here is what I need to do. I have very large csv files and I
wanted to create percentage changes. Should I try to change a to an
array?

I have a file that looks like this
x1 date1 y1 #
x1 date2 y1 #
...
x1 date1 y2 #
x1 date2 y2 #
...
x2 date1 y1 #
x2 date2 y1 #

I just want to returns only if columns 1 and 3 equal the next point in
the column.
Thanks again.
Michael
Brian Candler wrote:
> On Mon, Feb 12, 2007 at 08:05:01PM +0900, Michael Sc wrote:
>> else print 0
>> end}
>
> Why don't you give some sample data, and show what happens when you run
> it.
> Preferably make a small, standalone program which demonstrates the
> problem.
> Do you get an exception raised? A wrong result?
>

--
Posted via http://www.ruby-....

Brian Candler

2/12/2007 1:54:00 PM

0

> With this I get an error on the 3rd line of undefined method(-) for ".08
> #(the first number)#":String(NoMethodError)Print was able to do the
> calculation without the if statements.

I expect the problem is that a[x][y] contains a string, not an integer.

You can confirm this by adding

puts a.inspect

into your program just after you've read in the array, and look for
["0", "1", "2"] instead of [0, 1, 2]

To fix the problem, try adding some .to_i calls on the elements before
performing the arithmetic on them.

irb(main):001:0> a = "9"
=> "9"
irb(main):002:0> b = "6"
=> "6"
irb(main):003:0> a - b
NoMethodError: undefined method -' for "9":String
from (irb):3
irb(main):004:0> a.to_i - b.to_i
=> 3

Notice that the problem you have come across has nothing to with "if"
statements, nor with them being embedded in the "upto" construct. The moral:
try to avoid premature diagnosis :-)

Regards,

Brian.

Michael Sc

2/12/2007 2:26:00 PM

0

Brian,
Thank you very much. You are absolutely correct about the problem and
premature diagnosis.
Michael
Brian Candler wrote:
>
> Notice that the problem you have come across has nothing to with "if"
> statements, nor with them being embedded in the "upto" construct. The
> moral:
> try to avoid premature diagnosis :-)
>
> Regards,
>
> Brian.

--
Posted via http://www.ruby-....

Jeremy McAnally

2/12/2007 3:06:00 PM

0

Let's clean your syntax up a little bit first...

0.upto(a.size - 2) do |i|
if (a[i][2]==a[i+1][2] and a[i][0]==a[i+1][0])
print ((a[i+1][3] - a[i][3]) / a[i][3] * 100) / n
else
print 0
end
end

Looking at this, I (as someone else already stated) would make sure
that everything is a number rather than a string. It seems that if
you're having problems with the if statement, that's probably the
case. I would inspect the objects at every iterations (e.g., rather
than just printing 0, I would print a[i][2].inspect and
a[i+1][2].inspect or whatever). That should give you some insight as
to what's going on.

--Jeremy

On 2/12/07, Michael Sc <michael.schatzow@gmail.com> wrote:
> Thank you to everyone for all of your help.
> I was trying to use upto to go through an array of arrays while using if
> statments. Could anyone enlighten me on what I am doing wrong with the
> if statements?
> I am sure it is something easy.
>
> I tried this:
> 0.upto( a.size-2 ) {|i|
> if (a[i][2]==a[i+1][2] and a[i][0]==a[i+1][0]) then
> print { (a[i+1][3] - a[i][3]) / a[i][3] * 100 } /n
> else print 0
> end}
>
> Thanks again for all of the help.
> Michael
>
> --
> Posted via http://www.ruby-....
>
>


--
http://www.jeremymca...

My free Ruby e-book:
http://www.humblelittlerubybook...

My blogs:
http://www.mrneigh...
http://www.rubyinpra...

Michael Sc

2/12/2007 3:36:00 PM

0

thank you very much. I had an issue with the string. I adjusted the
code to the following. I knew it had to be something incredibly trivial.
Thank you all again.


y=0.upto(a.size - 2 ) do |i|
if (a[i][2]==a[i+1][2] and a[i][0]==a[i+1][0]) then
puts ((a[i+1][3].to_f - a[i][3].to_f) / a[i][3].to_f * 100)
else
puts 0
end








Jeremy McAnally wrote:
> Let's clean your syntax up a little bit first...
>
> 0.upto(a.size - 2) do |i|
> if (a[i][2]==a[i+1][2] and a[i][0]==a[i+1][0])
> print ((a[i+1][3] - a[i][3]) / a[i][3] * 100) / n
> else
> print 0
> end
> end
>
> Looking at this, I (as someone else already stated) would make sure
> that everything is a number rather than a string. It seems that if
> you're having problems with the if statement, that's probably the
> case. I would inspect the objects at every iterations (e.g., rather
> than just printing 0, I would print a[i][2].inspect and
> a[i+1][2].inspect or whatever). That should give you some insight as
> to what's going on.
>
> --Jeremy
>
> On 2/12/07, Michael Sc <michael.schatzow@gmail.com> wrote:
>> else print 0
>> end}
>>
>> Thanks again for all of the help.
>> Michael
>>
>> --
>> Posted via http://www.ruby-....
>>
>>
>
>
> --
> http://www.jeremymca...
>
> My free Ruby e-book:
> http://www.humblelittlerubybook...
>
> My blogs:
> http://www.mrneigh...
> http://www.rubyinpra...


--
Posted via http://www.ruby-....