Private method - Fixnum (NoMethodError)

Dear All,

I can’t find the error in my code. Can you explain me "private method

  • Fixnum (NoMethodError)"?

Many thanks in advance,

koko

def subtotal(qty = 1)
return nil if self.to_f <= 0 || qty.to_f <= 0
self.to_f * qty.to_f
end

apple = 11

puts apple.subtotal(2)

Hi,

In message “Re: private method - Fixnum (NoMethodError)”
on Thu, 18 Jun 2009 01:13:56 +0900, salai [email protected]
writes:

|I can’t find the error in my code. Can you explain me “private method
|- Fixnum (NoMethodError)”?

The actual error message is:

s.rb:8: private method `subtotal’ called for 11:Fixnum (NoMethodError)

and it means visibility of a method defined at the top level is
private. If you want to call subtotal in method form, you have to do
either

  • declare subtotal as public explicitly, using public :subtotal

  • or, re-open Fixnum and define subtotal in class definition

          matz.
    

Hi,

On Wed, Jun 17, 2009 at 9:13 AM, salai[email protected] wrote:

puts apple.subtotal(2)
You’ve defined the ‘subtotal’ method in the global scope, which is
equivalent to defining a private instance method on Object. Private
methods can’t be called with a receiver. If you really want to do this
(this method seems bizarre to me), you’ll want to reopen one or more
of the numeric classes and define your method there, e.g.,

class Fixnum
def subtotal qty = 1
return nil if to_f <= 0 || qty.to_f <= 0
to_f * qty.to_f
end
end

apple = 11

puts apple.subtotal(2)

22.0

~ j.

On Wednesday 17 June 2009, salai wrote:

| return nil if self.to_f <= 0 || qty.to_f <= 0
| self.to_f * qty.to_f
|end
|
|apple = 11
|
|puts apple.subtotal(2)

First of all, when you ask about an error, it’s better to report the
whole
error message, not just a bit of it. At any rate, running your code I
get the
error message:

private method `subtotal’ called for 11:Fixnum (NoMethodError)

this means that you’re calling a private method in a forbidden way, that
is
using the object.method_name notation. Private methods can only be
called on
the explicit receiver (self). Now you may be asking, “why subtotal is a
private method?” The answer is that methods defined toplevel (that is,
methods
which aren’t defined inside a module or a class and aren’t singleton
methods)
automatically become private methods of class Object, so you can’t call
them
with an explicit receiver.

You have at least two options to fix your code, depending on what
exactly you
need. You can:

  1. define your subtotal method like this:
    def subtotal( arg1, qty=1)
    return nil if arg1.to_f <= 0 || qty.to_f <= 0
    arg1.to_f * qty.to_f
    end

and transform apple from the explicit receiver of the call to the first
argument to subtotal:

puts subtotal(apple, 2)

  1. define the subtotal method in a class. For example, you can define it
    for
    the Fixnum class:

class Fixnum
def subtotal(qty = 1)
return nil if self.to_f <= 0 || qty.to_f <= 0
self.to_f * qty.to_f
end
end

then you can call it as you originally did:
puts apple.subtotal(2)

I hope this helps

Stefano

Thanks you very much to you all.

regards,
salai.