# Optional Message Parameters?

**URL:** <https://www.ruby-forum.com/t/optional-message-parameters/58372>\
**Category:** Ruby\
**Created:** [April 20, 2006, 11:48pm UTC](https://www.ruby-forum.com/t/optional-message-parameters/58372 "2006-04-20T23:48:56Z")\
**Posts on this page:** 8\
**Page:** 1

<div class="post-metadata">

**Author:** ![nko](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/n/91b2a8/32.png) [@nko](https://www.ruby-forum.com/u/nko)\
**Post date:** [April 20, 2006, 11:48pm UTC](https://www.ruby-forum.com/t/optional-message-parameters/58372/1 "2006-04-20T23:48:56Z")

</div>

(Warning: Newbie Altert!)

How do I write a method with optional params? I would think that this:

def do\_this(opt1="", opt2="")  
puts opt2  
end  
do\_this(opt2=“This”)

Would result in “This” being displayed. Instead, “This” becomes the  
value of opt1. I’d like to set opt1 and opt2 to default to “”. How do I  
do that?

---

<div class="post-metadata">

**Author:** ![nko](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/n/91b2a8/32.png) [@nko](https://www.ruby-forum.com/u/nko)\
**Post date:** [April 20, 2006, 11:54pm UTC](https://www.ruby-forum.com/t/optional-message-parameters/58372/2 "2006-04-20T23:54:01Z")

</div>

Nathan O. wrote:

> (Warning: Newbie Altert!)
> 
> How do I write a method with optional params? I would think that this:
> 
> def do\_this(opt1="", opt2="")  
> puts opt2  
> end  
> do\_this(opt2=“This”)
> 
> Would result in “This” being displayed. Instead, “This” becomes the  
> value of opt1. I’d like to set opt1 and opt2 to default to “”. How do I  
> do that?  
> Use a hash:

def do\_this( args )  
puts args[:opt2]  
end  
do\_this :opt2=\>“This” #=\> This

What you’re doing now is assigning to opt2 then passing it:

do\_this(opt2=“This”)  
puts opt2 #=\> “This”

---

<div class="post-metadata">

**Author:** ![nko](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/n/91b2a8/32.png) [@nko](https://www.ruby-forum.com/u/nko)\
**Post date:** [April 20, 2006, 11:57pm UTC](https://www.ruby-forum.com/t/optional-message-parameters/58372/3 "2006-04-20T23:57:07Z")

</div>

> Use a hash:
> 
> def do\_this( args )  
> puts args[:opt2]  
> end  
> do\_this :opt2=\>“This” #=\> This
> 
> What you’re doing now is assigning to opt2 then passing it:
> 
> do\_this(opt2=“This”)  
> puts opt2 #=\> “This”

I understand that this will work, but seems so inelegant. Is it really  
how this is supposed to be done?

---

<div class="post-metadata">

**Author:** ![nko](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/n/91b2a8/32.png) [@nko](https://www.ruby-forum.com/u/nko)\
**Post date:** [April 21, 2006, 12:01am UTC](https://www.ruby-forum.com/t/optional-message-parameters/58372/4 "2006-04-21T00:01:51Z")

</div>

On 4/20/06, Nathan O. [removed\_email\_address@domain.invalid](mailto:removed_email_address@domain.invalid) wrote:

> Would result in “This” being displayed. Instead, “This” becomes the  
> value of opt1. I’d like to set opt1 and opt2 to default to “”. How do I  
> do that?

This is usually a case where you either use \* or a hash parameter. \*  
is good for cases where you can distinguish by value. In your case it  
looks like a hash would be appropriate.

def do\_this(opts)  
puts opt[:two]  
end

do\_this(:two =\> “This”)

Notes: The hash parameter will always be the last parameter (ignoring  
& args and other odd parameter changes when using super). This means  
you can pass many things along side the hash, though the more you add  
the more complex it gets to manage the interface. Rails uses this  
technique heavily. Have a look at the find() code in ActiveRecord  
sometime to learn how they manage such an interface (much cleaner in  
more recent releases).

Future major versions of Ruby are going to have actual named  
parameters. So much to look forward to in 2.0!

Brian.

---

<div class="post-metadata">

**Author:** ![nko](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/n/91b2a8/32.png) [@nko](https://www.ruby-forum.com/u/nko)\
**Post date:** [April 21, 2006, 12:02am UTC](https://www.ruby-forum.com/t/optional-message-parameters/58372/5 "2006-04-21T00:02:26Z")

</div>

Nathan O. wrote:

> > Use a hash:
> > 
> > def do\_this( args )  
> > puts args[:opt2]  
> > end  
> > do\_this :opt2=\>“This” #=\> This
> > 
> > What you’re doing now is assigning to opt2 then passing it:
> > 
> > do\_this(opt2=“This”)  
> > puts opt2 #=\> “This”
> 
> I understand that this will work, but seems so inelegant. Is it really  
> how this is supposed to be done?

There are default values too:

def do\_this( opt1, opt2="" )  
puts opt2  
end

If that’s what you mean.

---

<div class="post-metadata">

**Author:** ![nko](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/n/91b2a8/32.png) [@nko](https://www.ruby-forum.com/u/nko)\
**Post date:** [April 21, 2006, 12:07am UTC](https://www.ruby-forum.com/t/optional-message-parameters/58372/6 "2006-04-21T00:07:50Z")

</div>

Brian M. wrote:

> On 4/20/06, Nathan O. [removed\_email\_address@domain.invalid](mailto:removed_email_address@domain.invalid) wrote:
> 
> > Would result in “This” being displayed. Instead, “This” becomes the  
> > value of opt1. I’d like to set opt1 and opt2 to default to “”. How do I  
> > do that?
> 
> This is usually a case where you either use \* or a hash parameter. \*  
> is good for cases where you can distinguish by value. In your case it  
> looks like a hash would be appropriate.
> 
> def do\_this(opts)  
> puts opt[:two]  
> end
> 
> do\_this(:two =\> “This”)

\*? I don’t even know how I’d google that 🙂

> Notes: The hash parameter will always be the last parameter (ignoring  
> & args and other odd parameter changes when using super). This means  
> you can pass many things along side the hash, though the more you add  
> the more complex it gets to manage the interface. Rails uses this  
> technique heavily. Have a look at the find() code in ActiveRecord  
> sometime to learn how they manage such an interface (much cleaner in  
> more recent releases).

_Woosh!_ That was the sound of this discussion going over my head at  
Mach 2!

> Future major versions of Ruby are going to have actual named  
> parameters. So much to look forward to in 2.0!

Definitely looking forward to that!

---

<div class="post-metadata">

**Author:** ![nko](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/n/91b2a8/32.png) [@nko](https://www.ruby-forum.com/u/nko)\
**Post date:** [April 21, 2006, 12:18am UTC](https://www.ruby-forum.com/t/optional-message-parameters/58372/7 "2006-04-21T00:18:34Z")

</div>

> \*? I don’t even know how I’d google that 🙂

The star is used to have fun with parameters. Watch:

def have\_fun(\*args)  
args.each{|arg| puts arg}  
end

have\_fun 1, 2, 3 # outputs 1, 2, 3

It basically takes any additional parameters provided and puts it into  
an array (with the exception of blocks):

def some\_args( opt1, opt2, \*otheropts )  
otheropts  
end

some\_args nil, nil, “have”, “fun” # =\> [“have”, “fun”]

You can use it the other way to:

arguments = [“Hello”, “world”]  
send(“puts”, \*arguments) # Outputs the arguments

See [http://redhanded.hobix.com/bits/wonderOfTheWhenBeFlat.html](http://redhanded.hobix.com/bits/wonderOfTheWhenBeFlat.html) for  
creative uses.

---

<div class="post-metadata">

**Author:** ![nko](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/n/91b2a8/32.png) [@nko](https://www.ruby-forum.com/u/nko)\
**Post date:** [April 23, 2006, 6:57am UTC](https://www.ruby-forum.com/t/optional-message-parameters/58372/8 "2006-04-23T06:57:54Z")

</div>

On 4/20/06, Nathan O. [removed\_email\_address@domain.invalid](mailto:removed_email_address@domain.invalid) wrote:

> Would result in “This” being displayed. Instead, “This” becomes the  
> value of opt1. I’d like to set opt1 and opt2 to default to “”. How do I  
> do that?

Nathan, looks like you’re expecting Ruby to be like Python, but Ruby  
doesn’t have keyword args – it just looks at the order of the stuff  
pass in to a method, and assigns them to the method parameters in that  
order.

In the method call you show above (do\_this(opt2=“This”)), what’s  
happening (I think) is that some local variable named opt2 (local to  
the arg list?) is being created in your argument list, and then the  
string “This” is being assigned to it. Then, after that business is  
done being evaluated, that string gets passed into the method where  
it’s assigned to parameter opt1.
