user2851669
user2851669

Reputation:

Argument Error : Wrong number of arguments

I am writing the following in rails console.

> class Hello
>   def method
>     d = Jobs.find_by_sql("select id, count(*) as TOTAL from table group by id having count>100")
>     d.each do |m|
>         puts m.account_id
>       end
>     end
>   end

 => :method 
> Hello.method
ArgumentError: wrong number of arguments (0 for 1)

I can't figure out what's wrong in this code. How can I solve this error.

Upvotes: 0

Views: 1217

Answers (1)

Max Williams
Max Williams

Reputation: 32955

your method name "method" is an existing method of the Object class, which is ultimately inherited by all classes in ruby.

You define an instance method with this name, which would be fine and would override the inherited instance method if it existed already. However, when you come to call it, you're calling it as a class method (because you're calling it on Hello, which is the class), so you're calling the existing "method" method, which is complaining about not getting any parameters.

Change your method to be called "foo" and then try to do Hello.foo. You'll get an "undefined method or variable" error because there's no foo class method.

Then do

hello = Hello.new
hello.foo

and it will work.

EDIT:

If you want it to actually be a class method, then you can do it via either of these ways:

class Hello

  def self.method
    d = Jobs.find_by_sql("select id, count(*) as TOTAL from table group by id having count>100")
    d.each do |m|
        puts m.account_id
      end
    end
  end

end

or

class Hello

  #class methods go in here 
  class << self

    def method
      d = Jobs.find_by_sql("select id, count(*) as TOTAL from table group by id having count>100")
      d.each do |m|
          puts m.account_id
        end
      end
    end

  end
end

As an aside, it's a convention, and generally a good idea, to use meaningful variable names. For example, if you have a variable which is a collection of Job objects, call it "jobs", not "d". Then anyone reading your code can easily remember what is held in that variable.

Using this principle, i would rewrite your code thus:

    def output_job_account_ids
      jobs = Jobs.find_by_sql("select id, count(*) as TOTAL from table group by id having count>100")
      jobs.each do |job|
          puts job.account_id
        end
      end
    end

See how it's immediately much more obvious what is happening? I renamed the method name too: it's generally a good idea to have a method name describe what the method does.

Upvotes: 4

Related Questions