# Chomping and stomping

**URL:** <https://rubytalk.org/t/chomping-and-stomping/24559>\
**Category:** ruby-talk\
**Created:** [2 February 2006 15:11 UTC](https://rubytalk.org/t/chomping-and-stomping/24559 "2006-02-02T15:11:52Z")\
**Posts on this page:** 17\
**Page:** 1

<div class="post-metadata">

**Author:** ![John\_Maclean](https://avatars.discourse-cdn.com/v4/letter/j/e8c25b/32.png) [@John\_Maclean](https://rubytalk.org/u/John_Maclean)\
**Post date:** [2 February 2006 15:11 UTC](https://rubytalk.org/t/chomping-and-stomping/24559/1 "2006-02-02T15:11:52Z")

</div>

Chaps,

Here's a short script to keep requesting for input...

#!/usr/bin/ruby -w  
def chomper  
&nbsp;&nbsp;xx = gets.chomp!  
&nbsp;&nbsp;until $\_ == "qq"  
&nbsp;&nbsp;&nbsp;&nbsp;puts "hit me with a squirell!"  
&nbsp;&nbsp;&nbsp;&nbsp;xx = gets.chomp!  
&nbsp;&nbsp;&nbsp;&nbsp;xx  
&nbsp;&nbsp;end  
end

chomper

# this works but surely there must be a way to incoporate a variable  
in there?

#!/usr/bin/ruby -w  
def chomper  
&nbsp;&nbsp;xx = gets.chomp!  
&nbsp;&nbsp;until xx == "qq"  
&nbsp;&nbsp;&nbsp;&nbsp;puts "hit me with a squirell!"  
&nbsp;&nbsp;&nbsp;&nbsp;xx  
&nbsp;&nbsp;end  
end

#this don't work.

> **···**
>
> --  
> John Maclean  
> MSc (DIC)  
> 07739 171 531

---

<div class="post-metadata">

**Author:** ![Jacob\_Fugal](https://avatars.discourse-cdn.com/v4/letter/j/439d5e/32.png) [@Jacob\_Fugal](https://rubytalk.org/u/Jacob_Fugal)\
**Post date:** [2 February 2006 17:16 UTC](https://rubytalk.org/t/chomping-and-stomping/24559/2 "2006-02-02T17:16:11Z")

</div>

String#chomp! is a "destructive" operation. This means that it acts in  
place on its receiver and, in this case, returns nil. So what's  
happening here is that Kernel#gets creates a String object, chomp! is  
sent to that object, the object is modified in place and nil returned.  
That's why xx is nil. As you discovered in your first example, the  
String object returned by Kernel#gets is stored in $\_. Accessing it  
this way isn't a bset practice however.

What you probably want instead is to use the non-destructive twin (the  
Good Twin) of String#chomp!, namely String#chomp. Notice the lack of  
the bang (!). The bang is generally (but not always) an indicator that  
the method is destructive. String#chomp creates a chomped copy of it's  
receiver and returns it. Replacing chomp! with chomp it should work:

&nbsp;&nbsp;#!/usr/bin/ruby -w  
&nbsp;&nbsp;def chomper  
&nbsp;&nbsp;&nbsp;&nbsp;xx = gets.chomp  
&nbsp;&nbsp;&nbsp;&nbsp;until xx == "qq"  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;puts "hit me with a squirell!"  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;xx  
&nbsp;&nbsp;&nbsp;&nbsp;end  
&nbsp;&nbsp;end

&nbsp;&nbsp;puts chomper

Jacob Fugal

> **···**
>
> On 2/2/06, John Maclean \<info@jayeola.org\> wrote:
> 
> > #!/usr/bin/ruby -w  
> > def chomper  
> > &nbsp;&nbsp;xx = gets.chomp!  
> > &nbsp;&nbsp;until $\_ == "qq"  
> > &nbsp;&nbsp;&nbsp;&nbsp;puts "hit me with a squirell!"  
> > &nbsp;&nbsp;&nbsp;&nbsp;xx = gets.chomp!  
> > &nbsp;&nbsp;&nbsp;&nbsp;xx  
> > &nbsp;&nbsp;end  
> > end
> > 
> > chomper
> > 
> > # this works but surely there must be a way to incoporate a variable  
> > in there?
> > 
> > #!/usr/bin/ruby -w  
> > def chomper  
> > &nbsp;&nbsp;xx = gets.chomp!  
> > &nbsp;&nbsp;until xx == "qq"  
> > &nbsp;&nbsp;&nbsp;&nbsp;puts "hit me with a squirell!"  
> > &nbsp;&nbsp;&nbsp;&nbsp;xx  
> > &nbsp;&nbsp;end  
> > end
> > 
> > #this don't work.

---

<div class="post-metadata">

**Author:** ![W\_James](https://avatars.discourse-cdn.com/v4/letter/w/e274bd/32.png) [@W\_James](https://rubytalk.org/u/W_James)\
**Post date:** [2 February 2006 17:28 UTC](https://rubytalk.org/t/chomping-and-stomping/24559/3 "2006-02-02T17:28:19Z")

</div>

John Maclean wrote:

> Chaps,
> 
> Here's a short script to keep requesting for input...
> 
> #!/usr/bin/ruby -w  
> def chomper  
> &nbsp;&nbsp;xx = gets.chomp!  
> &nbsp;&nbsp;until $\_ == "qq"  
> &nbsp;&nbsp;&nbsp;&nbsp;puts "hit me with a squirell!"  
> &nbsp;&nbsp;&nbsp;&nbsp;xx = gets.chomp!  
> &nbsp;&nbsp;&nbsp;&nbsp;xx  
> &nbsp;&nbsp;end  
> end
> 
> chomper
> 
> # this works but surely there must be a way to incoporate a variable  
> in there?
> 
> #!/usr/bin/ruby -w  
> def chomper  
> &nbsp;&nbsp;xx = gets.chomp!  
> &nbsp;&nbsp;until xx == "qq"  
> &nbsp;&nbsp;&nbsp;&nbsp;puts "hit me with a squirell!"  
> &nbsp;&nbsp;&nbsp;&nbsp;xx  
> &nbsp;&nbsp;end  
> end
> 
> #this don't work.

def chomper  
&nbsp;&nbsp;until (xx = gets.chomp) == 'qq'  
&nbsp;&nbsp;&nbsp;&nbsp;puts "hit me with a squirell!"  
&nbsp;&nbsp;end  
&nbsp;&nbsp;xx  
end

puts chomper

---

<div class="post-metadata">

**Author:** ![Ara.T.Howard6](https://avatars.discourse-cdn.com/v4/letter/a/958977/32.png) [@Ara.T.Howard6](https://rubytalk.org/u/Ara.T.Howard6)\
**Post date:** [2 February 2006 17:38 UTC](https://rubytalk.org/t/chomping-and-stomping/24559/4 "2006-02-02T17:38:27Z")

</div>

harp:~ \> cat a.rb  
&nbsp;&nbsp;&nbsp;def chomper  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;until (xx = gets.chomp) == 'qq'  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;puts "hit me with a squirell!"  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;end  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;xx  
&nbsp;&nbsp;&nbsp;end

&nbsp;&nbsp;&nbsp;puts chomper

&nbsp;&nbsp;&nbsp;harp:~ \> ruby a.rb \< /dev/null  
&nbsp;&nbsp;&nbsp;a.rb:3:in `chomper': private method `chomp' called for nil:NilClass (NoMethodError)  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;from a.rb:9

nil doesn't like that! 😉

-a

> **···**
>
> On Fri, 3 Feb 2006, William James wrote:
> 
> > John Maclean wrote:
> > 
> > > Chaps,
> > > 
> > > Here's a short script to keep requesting for input...
> > > 
> > > #!/usr/bin/ruby -w  
> > > def chomper  
> > > &nbsp;&nbsp;xx = gets.chomp!  
> > > &nbsp;&nbsp;until $\_ == "qq"  
> > > &nbsp;&nbsp;&nbsp;&nbsp;puts "hit me with a squirell!"  
> > > &nbsp;&nbsp;&nbsp;&nbsp;xx = gets.chomp!  
> > > &nbsp;&nbsp;&nbsp;&nbsp;xx  
> > > &nbsp;&nbsp;end  
> > > end
> > > 
> > > chomper
> > > 
> > > # this works but surely there must be a way to incoporate a variable  
> > > in there?
> > > 
> > > #!/usr/bin/ruby -w  
> > > def chomper  
> > > &nbsp;&nbsp;xx = gets.chomp!  
> > > &nbsp;&nbsp;until xx == "qq"  
> > > &nbsp;&nbsp;&nbsp;&nbsp;puts "hit me with a squirell!"  
> > > &nbsp;&nbsp;&nbsp;&nbsp;xx  
> > > &nbsp;&nbsp;end  
> > > end
> > > 
> > > #this don't work.
> > 
> > def chomper  
> > until (xx = gets.chomp) == 'qq'  
> > &nbsp;&nbsp;&nbsp;puts "hit me with a squirell!"  
> > end  
> > xx  
> > end
> > 
> > puts chomper
> 
> --  
> happiness is not something ready-made. it comes from your own actions.  
> - h.h. the 14th dali lama

---

<div class="post-metadata">

**Author:** ![John\_Maclean](https://avatars.discourse-cdn.com/v4/letter/j/e8c25b/32.png) [@John\_Maclean](https://rubytalk.org/u/John_Maclean)\
**Post date:** [2 February 2006 18:29 UTC](https://rubytalk.org/t/chomping-and-stomping/24559/5 "2006-02-02T18:29:54Z")

</div>

Chaps,

Thanks for those speedy replies  
Following on from

#thanks to you guyson the list for clearing this up  
jayeola@tp20$ cat bin/acid/classes/testing/testchomp.rb  
#!/usr/bin/ruby -w  
def chomper  
&nbsp;&nbsp;xx = gets.chomp  
&nbsp;&nbsp;until (xx= gets.chomp) == "qq"  
&nbsp;&nbsp;&nbsp;&nbsp;puts "hit me with a squirell!"  
&nbsp;&nbsp;end  
&nbsp;&nbsp;xx  
end

chomper  
# ^^ the above works. 🙂

# This is supposed to do the same as the above but write to a file...

here's version 1  
#!/usr/bin/ruby -w

def testwrite  
&nbsp;&nbsp;puts "hit me with a squirell!"  
&nbsp;&nbsp;until $\_ =="qq"  
&nbsp;&nbsp;&nbsp;&nbsp;gets.chomp!  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if $\_ != "qq"  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;File.open("testfile", "a") { |file| file.write($\_) }  
end  
end  
end  
testwrite

here's version 1

jayeola@tp20$ cat bin/acid/classes/testing/write\_file2.rb  
#!/usr/bin/ruby -w

def testwrite  
&nbsp;&nbsp;xx = gets.chomp  
&nbsp;&nbsp;until (xx.gets.chomp) == "qq"  
&nbsp;&nbsp;&nbsp;&nbsp;puts "hit me with a squirell!"  
&nbsp;&nbsp;&nbsp;&nbsp;File.open("testfile", "a") { |file| file.write(xx) }  
&nbsp;&nbsp;end  
end

testwrite

> **···**
>
> On Fri, 3 Feb 2006 02:16:11 +0900 Jacob Fugal \<lukfugl@gmail.com\> wrote:
> 
> > On 2/2/06, John Maclean \<info@jayeola.org\> wrote:  
> > \> #!/usr/bin/ruby -w  
> > \> def chomper  
> > \> xx = gets.chomp!  
> > \> until $\_ == "qq"  
> > \> puts "hit me with a squirell!"  
> > \> xx = gets.chomp!  
> > \> xx  
> > \> end  
> > \> end  
> > \>  
> > \> chomper  
> > \>  
> > \> # this works but surely there must be a way to incoporate a variable  
> > \> in there?  
> > \>  
> > \> #!/usr/bin/ruby -w  
> > \> def chomper  
> > \> xx = gets.chomp!  
> > \> until xx == "qq"  
> > \> puts "hit me with a squirell!"  
> > \> xx  
> > \> end  
> > \> end  
> > \>  
> > \> #this don't work.
> > 
> > String#chomp! is a "destructive" operation. This means that it acts in  
> > place on its receiver and, in this case, returns nil. So what's  
> > happening here is that Kernel#gets creates a String object, chomp! is  
> > sent to that object, the object is modified in place and nil returned.  
> > That's why xx is nil. As you discovered in your first example, the  
> > String object returned by Kernel#gets is stored in $\_. Accessing it  
> > this way isn't a bset practice however.
> > 
> > What you probably want instead is to use the non-destructive twin (the  
> > Good Twin) of String#chomp!, namely String#chomp. Notice the lack of  
> > the bang (!). The bang is generally (but not always) an indicator that  
> > the method is destructive. String#chomp creates a chomped copy of it's  
> > receiver and returns it. Replacing chomp! with chomp it should work:
> > 
> > &nbsp;&nbsp;#!/usr/bin/ruby -w  
> > &nbsp;&nbsp;def chomper  
> > &nbsp;&nbsp;&nbsp;&nbsp;xx = gets.chomp  
> > &nbsp;&nbsp;&nbsp;&nbsp;until xx == "qq"  
> > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;puts "hit me with a squirell!"  
> > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;xx  
> > &nbsp;&nbsp;&nbsp;&nbsp;end  
> > &nbsp;&nbsp;end
> > 
> > &nbsp;&nbsp;puts chomper
> > 
> > Jacob Fugal
> 
> --  
> John Maclean  
> MSc (DIC)  
> 07739 171 531

---

<div class="post-metadata">

**Author:** ![W\_James](https://avatars.discourse-cdn.com/v4/letter/w/e274bd/32.png) [@W\_James](https://rubytalk.org/u/W_James)\
**Post date:** [2 February 2006 19:13 UTC](https://rubytalk.org/t/chomping-and-stomping/24559/6 "2006-02-02T19:13:18Z")

</div>

William James wrote:

> John Maclean wrote:  
> \> Chaps,  
> \>  
> \> Here's a short script to keep requesting for input...  
> \>  
> \> #!/usr/bin/ruby -w  
> \> def chomper  
> \> xx = gets.chomp!  
> \> until $\_ == "qq"  
> \> puts "hit me with a squirell!"  
> \> xx = gets.chomp!  
> \> xx  
> \> end  
> \> end  
> \>  
> \> chomper  
> \>  
> \> # this works but surely there must be a way to incoporate a variable  
> \> in there?  
> \>  
> \> #!/usr/bin/ruby -w  
> \> def chomper  
> \> xx = gets.chomp!  
> \> until xx == "qq"  
> \> puts "hit me with a squirell!"  
> \> xx  
> \> end  
> \> end  
> \>  
> \> #this don't work.
> 
> def chomper  
> &nbsp;&nbsp;until (xx = gets.chomp) == 'qq'  
> &nbsp;&nbsp;&nbsp;&nbsp;puts "hit me with a squirell!"  
> &nbsp;&nbsp;end  
> &nbsp;&nbsp;xx  
> end
> 
> puts chomper

def chomper  
&nbsp;&nbsp;puts "Hit me!" while gets and $\_.chomp! != "qq"  
&nbsp;&nbsp;$\_ if $\_  
end

---

<div class="post-metadata">

**Author:** ![Jacob\_Fugal](https://avatars.discourse-cdn.com/v4/letter/j/439d5e/32.png) [@Jacob\_Fugal](https://rubytalk.org/u/Jacob_Fugal)\
**Post date:** [2 February 2006 17:59 UTC](https://rubytalk.org/t/chomping-and-stomping/24559/7 "2006-02-02T17:59:26Z")

</div>

Heh, yeah, I glossed over that too. You really need to check the  
result of gets before you chomp it. This is the way I'd write John's  
original loop (same semantics):

&nbsp;&nbsp;def chomper  
&nbsp;&nbsp;&nbsp;&nbsp;while xx = gets  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;xx.chomp!  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;break if xx == 'qq'  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;puts "hit me with a squirell!"  
&nbsp;&nbsp;&nbsp;&nbsp;end  
&nbsp;&nbsp;&nbsp;&nbsp;xx  
&nbsp;&nbsp;end

and the way I'd write it for myself (different semantics, mostly same intent):

&nbsp;&nbsp;def chomped\_gets  
&nbsp;&nbsp;&nbsp;&nbsp;(s = gets) and s.chomp  
&nbsp;&nbsp;end

&nbsp;&nbsp;def chomper  
&nbsp;&nbsp;&nbsp;&nbsp;loop do  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;puts "hit me with a squirell!"  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;break unless xx = chomped\_gets  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;return xx if xx == 'qq'  
&nbsp;&nbsp;&nbsp;&nbsp;end  
&nbsp;&nbsp;end

Jacob Fugal

> **···**
>
> On 2/2/06, ara.t.howard@noaa.gov \<ara.t.howard@noaa.gov\> wrote:
> 
> > &nbsp;&nbsp;&nbsp;harp:~ \> ruby a.rb \< /dev/null  
> > &nbsp;&nbsp;&nbsp;a.rb:3:in `chomper': private method `chomp' called for nil:NilClass (NoMethodError)  
> > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;from a.rb:9
> > 
> > nil doesn't like that! 😉

---

<div class="post-metadata">

**Author:** ![Jacob\_Fugal](https://avatars.discourse-cdn.com/v4/letter/j/439d5e/32.png) [@Jacob\_Fugal](https://rubytalk.org/u/Jacob_Fugal)\
**Post date:** [2 February 2006 19:41 UTC](https://rubytalk.org/t/chomping-and-stomping/24559/8 "2006-02-02T19:41:58Z")

</div>

This will always loop until EOF and then return nil. $\_.chomp! (as  
opposed to $\_.chomp) returns nil, and nil != "qq".

Jacob Fugal

PS. And let's not golf with this please...

> **···**
>
> On 2/2/06, William James \<w\_a\_x\_man@yahoo.com\> wrote:
> 
> > def chomper  
> > &nbsp;&nbsp;puts "Hit me!" while gets and $\_.chomp! != "qq"  
> > &nbsp;&nbsp;$\_ if $\_  
> > end

---

<div class="post-metadata">

**Author:** ![W\_James](https://avatars.discourse-cdn.com/v4/letter/w/e274bd/32.png) [@W\_James](https://rubytalk.org/u/W_James)\
**Post date:** [2 February 2006 19:43 UTC](https://rubytalk.org/t/chomping-and-stomping/24559/9 "2006-02-02T19:43:17Z")

</div>

The error I get in a dos-box is  
The system cannot find the path specified.

To produce the error you gave, I must do it this way:  
ruby a.rb \< nul:

When you post something that depends upon a particular  
operating system, you need to make that dependency clear.

It is reasonable to write a program that requires input.  
It is not reasonable to expect a program that requires input to  
function properly when you deliberately deprive it of input.

> **···**
>
> ara.t.howard@noaa.gov wrote:
> 
> > On Fri, 3 Feb 2006, William James wrote:
> > 
> > \>  
> > \> John Maclean wrote:  
> > \>\> Chaps,  
> > \>\>  
> > \>\> Here's a short script to keep requesting for input...  
> > \>\>  
> > \>\> #!/usr/bin/ruby -w  
> > \>\> def chomper  
> > \>\> xx = gets.chomp!  
> > \>\> until $\_ == "qq"  
> > \>\> puts "hit me with a squirell!"  
> > \>\> xx = gets.chomp!  
> > \>\> xx  
> > \>\> end  
> > \>\> end  
> > \>\>  
> > \>\> chomper  
> > \>\>  
> > \>\> # this works but surely there must be a way to incoporate a variable  
> > \>\> in there?  
> > \>\>  
> > \>\> #!/usr/bin/ruby -w  
> > \>\> def chomper  
> > \>\> xx = gets.chomp!  
> > \>\> until xx == "qq"  
> > \>\> puts "hit me with a squirell!"  
> > \>\> xx  
> > \>\> end  
> > \>\> end  
> > \>\>  
> > \>\> #this don't work.  
> > \>  
> > \>  
> > \> def chomper  
> > \> until (xx = gets.chomp) == 'qq'  
> > \> puts "hit me with a squirell!"  
> > \> end  
> > \> xx  
> > \> end  
> > \>  
> > \> puts chomper
> > 
> > &nbsp;&nbsp;&nbsp;harp:~ \> cat a.rb  
> > &nbsp;&nbsp;&nbsp;def chomper  
> > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;until (xx = gets.chomp) == 'qq'  
> > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;puts "hit me with a squirell!"  
> > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;end  
> > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;xx  
> > &nbsp;&nbsp;&nbsp;end
> > 
> > &nbsp;&nbsp;&nbsp;puts chomper
> > 
> > &nbsp;&nbsp;&nbsp;harp:~ \> ruby a.rb \< /dev/null  
> > &nbsp;&nbsp;&nbsp;a.rb:3:in `chomper': private method `chomp' called for nil:NilClass (NoMethodError)  
> > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;from a.rb:9

---

<div class="post-metadata">

**Author:** ![W\_James](https://avatars.discourse-cdn.com/v4/letter/w/e274bd/32.png) [@W\_James](https://rubytalk.org/u/W_James)\
**Post date:** [2 February 2006 19:48 UTC](https://rubytalk.org/t/chomping-and-stomping/24559/10 "2006-02-02T19:48:18Z")

</div>

William James wrote:

> William James wrote:  
> \> John Maclean wrote:  
> \> \> Chaps,  
> \> \>  
> \> \> Here's a short script to keep requesting for input...  
> \> \>  
> \> \> #!/usr/bin/ruby -w  
> \> \> def chomper  
> \> \> xx = gets.chomp!  
> \> \> until $\_ == "qq"  
> \> \> puts "hit me with a squirell!"  
> \> \> xx = gets.chomp!  
> \> \> xx  
> \> \> end  
> \> \> end  
> \> \>  
> \> \> chomper  
> \> \>  
> \> \> # this works but surely there must be a way to incoporate a variable  
> \> \> in there?  
> \> \>  
> \> \> #!/usr/bin/ruby -w  
> \> \> def chomper  
> \> \> xx = gets.chomp!  
> \> \> until xx == "qq"  
> \> \> puts "hit me with a squirell!"  
> \> \> xx  
> \> \> end  
> \> \> end  
> \> \>  
> \> \> #this don't work.  
> \>  
> \>  
> \> def chomper  
> \> until (xx = gets.chomp) == 'qq'  
> \> puts "hit me with a squirell!"  
> \> end  
> \> xx  
> \> end  
> \>  
> \> puts chomper
> 
> def chomper  
> &nbsp;&nbsp;puts "Hit me!" while gets and $\_.chomp! != "qq"  
> &nbsp;&nbsp;$\_ if $\_  
> end

def chomper  
&nbsp;&nbsp;puts "Hit me!" while gets and $\_.chomp! != "qq"  
&nbsp;&nbsp;$\_  
end

---

<div class="post-metadata">

**Author:** ![James\_Edward\_Gray\_II](https://avatars.discourse-cdn.com/v4/letter/j/ea5d25/32.png) [@James\_Edward\_Gray\_II](https://rubytalk.org/u/James_Edward_Gray_II)\
**Post date:** [2 February 2006 18:35 UTC](https://rubytalk.org/t/chomping-and-stomping/24559/11 "2006-02-02T18:35:36Z")

</div>

> > &nbsp;&nbsp;&nbsp;harp:~ \> ruby a.rb \< /dev/null  
> > &nbsp;&nbsp;&nbsp;a.rb:3:in `chomper': private method `chomp' called for nil:NilClass (NoMethodError)  
> > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;from a.rb:9
> > 
> > nil doesn't like that! 😉
> 
> Heh, yeah, I glossed over that too. You really need to check the  
> result of gets before you chomp it.

Isn't this why we have iterators in Ruby? We get to avoid all these messy loop ending tests...

> This is the way I'd write John's original loop (same semantics):
> 
> &nbsp;&nbsp;def chomper  
> &nbsp;&nbsp;&nbsp;&nbsp;while xx = gets  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;xx.chomp!  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;break if xx == 'qq'  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;puts "hit me with a squirell!"  
> &nbsp;&nbsp;&nbsp;&nbsp;end  
> &nbsp;&nbsp;&nbsp;&nbsp;xx  
> &nbsp;&nbsp;end

def chomper  
&nbsp;&nbsp;&nbsp;$stdin.each do |line|  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;line.chomp!

&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;return line if line == "qq"

&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;puts "Hit me with a squirrel!"  
&nbsp;&nbsp;&nbsp;end  
end

James Edward Gray II

> **···**
>
> On Feb 2, 2006, at 11:59 AM, Jacob Fugal wrote:
> 
> > On 2/2/06, ara.t.howard@noaa.gov \<ara.t.howard@noaa.gov\> wrote:

---

<div class="post-metadata">

**Author:** ![Jacob\_Fugal](https://avatars.discourse-cdn.com/v4/letter/j/439d5e/32.png) [@Jacob\_Fugal](https://rubytalk.org/u/Jacob_Fugal)\
**Post date:** [2 February 2006 19:51 UTC](https://rubytalk.org/t/chomping-and-stomping/24559/12 "2006-02-02T19:51:46Z")

</div>

> \> harp:~ \> ruby a.rb \< /dev/null  
> \> a.rb:3:in `chomper': private method `chomp' called for nil:NilClass (NoMethodError)  
> \> from a.rb:9
> 
> The error I get in a dos-box is  
> The system cannot find the path specified.
> 
> To produce the error you gave, I must do it this way:  
> ruby a.rb \< nul:
> 
> When you post something that depends upon a particular  
> operating system, you need to make that dependency clear.

Well, in Ara's defense I would claim that prefixing the command with  
"harp:~ \>" and using "/dev/null" both should be clear indicators that  
he's talking about a \*nix system.

> It is reasonable to write a program that requires input.  
> It is not reasonable to expect a program that requires input to  
> function properly when you deliberately deprive it of input.

This problem is not only due to no input. The same error will arise if  
you reach EOF before matching the expected line. Try this:

> echo "Hello" | ruby a.rb

It \*is\* reasonable to expect a program that requires input to function  
properly when invalid input is provided. Maybe the proper action is to  
raise an error, but it should be a contextually appropriate error.

Jacob Fugal

> **···**
>
> On 2/2/06, William James \<w\_a\_x\_man@yahoo.com\> wrote:
> 
> > ara.t.howard@noaa.gov wrote:

---

<div class="post-metadata">

**Author:** ![Ara.T.Howard6](https://avatars.discourse-cdn.com/v4/letter/a/958977/32.png) [@Ara.T.Howard6](https://rubytalk.org/u/Ara.T.Howard6)\
**Post date:** [2 February 2006 19:59 UTC](https://rubytalk.org/t/chomping-and-stomping/24559/13 "2006-02-02T19:59:16Z")

</div>

> The error I get in a dos-box is The system cannot find the path specified.
> 
> To produce the error you gave, I must do it this way: ruby a.rb \< nul:
> 
> When you post something that depends upon a particular operating system, you  
> need to make that dependency clear.

indeed. that's what specifying cat and /dev/null does in and least four ways:

&nbsp;&nbsp;&nbsp;cat, the most ubiquitous of unix programs =\> \*nix  
&nbsp;&nbsp;&nbsp;/ as file separator =\> \*nix  
&nbsp;&nbsp;&nbsp;/dev file system =\> \*nix  
&nbsp;&nbsp;&nbsp;/dev/null device =\> \*nix

😉

> It is reasonable to write a program that requires input. It is not  
> reasonable to expect a program that requires input to function properly when  
> you deliberately deprive it of input.

that's not what is happening. reading from /dev/null or nul is the same as  
reading from an empty file. the key point i was illustrating, and the bug in  
the program, is that is fails at eof regardless if input is given.

for example, if i run this from the shell and type 'ctrl-d' to signal end of  
input (on unix)

&nbsp;&nbsp;&nbsp;harp:~ \> cat a.rb  
&nbsp;&nbsp;&nbsp;def chomper  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;until (xx = gets.chomp) == 'qq'  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;puts "hit me with a squirell!"  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;end  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;xx  
&nbsp;&nbsp;&nbsp;end

&nbsp;&nbsp;&nbsp;puts chomper

&nbsp;&nbsp;&nbsp;harp:~ \> ruby a.rb  
&nbsp;&nbsp;&nbsp;a.rb:2:in `chomper': private method `chomp' called for nil:NilClass (NoMethodError)  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;from a.rb:8

running on an empty file does the same

&nbsp;&nbsp;&nbsp;harp:~ \> touch empty  
&nbsp;&nbsp;&nbsp;harp:~ \> ruby a.rb \< empty  
&nbsp;&nbsp;&nbsp;a.rb:2:in `chomper': private method `chomp' called for nil:NilClass (NoMethodError)  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;from a.rb:8

as does running with some input

&nbsp;&nbsp;&nbsp;harp:~ \> echo 42 \> input

&nbsp;&nbsp;&nbsp;harp:~ \> ruby a.rb \< input  
&nbsp;&nbsp;&nbsp;hit me with a squirell!  
&nbsp;&nbsp;&nbsp;a.rb:2:in `chomper': private method `chomp' called for nil:NilClass (NoMethodError)  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;from a.rb:8

in fact, it cannot be made to work with any input

it's important, imho only perhaps, to show working code (best done by actually  
showing a run) unless that code is noted to be un-tested. i make efforts to do  
this for all examples i post:

&nbsp;&nbsp;&nbsp;[http://groups.google.com/group/comp.lang.ruby/search?q=howard+cat+a.rb&start=0&scoring=d&](http://groups.google.com/group/comp.lang.ruby/search?q=howard+cat+a.rb&start=0&scoring=d&)

some probably find it anoying but i make too many mistakes otherwise.

kind regards.

-a

> **···**
>
> On Fri, 3 Feb 2006, William James wrote:
> 
> --  
> happiness is not something ready-made. it comes from your own actions.  
> - h.h. the 14th dali lama

---

<div class="post-metadata">

**Author:** ![W\_James](https://avatars.discourse-cdn.com/v4/letter/w/e274bd/32.png) [@W\_James](https://rubytalk.org/u/W_James)\
**Post date:** [2 February 2006 20:08 UTC](https://rubytalk.org/t/chomping-and-stomping/24559/14 "2006-02-02T20:08:18Z")

</div>

Jacob Fugal wrote:

> \> def chomper  
> \> puts "Hit me!" while gets and $\_.chomp! != "qq"  
> \> $\_ if $\_  
> \> end
> 
> This will always loop until EOF and then return nil. $\_.chomp! (as  
> opposed to $\_.chomp) returns nil, and nil != "qq".

It works under ruby 1.8.2 (2004-05-19) [i386-mswin32].  
Did you test it? The code you posted earlier doesn't work:

&nbsp;&nbsp;#!/usr/bin/ruby -w  
&nbsp;&nbsp;def chomper  
&nbsp;&nbsp;&nbsp;&nbsp;xx = gets.chomp  
&nbsp;&nbsp;&nbsp;&nbsp;until xx == "qq"  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;puts "hit me with a squirell!"  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;xx  
&nbsp;&nbsp;&nbsp;&nbsp;end  
&nbsp;&nbsp;end

&nbsp;&nbsp;puts chomper

Always test the code that you post, please.

> Jacob Fugal
> 
> PS. And let's not golf with this please...

If you don't like golf, why watch it?

def chomper  
&nbsp;&nbsp;puts "Hit me!" while gets.chomp! != "qq"  
&nbsp;&nbsp;$\_  
end

> **···**
>
> > On 2/2/06, William James \<w\_a\_x\_man@yahoo.com\> wrote:

---

<div class="post-metadata">

**Author:** ![Ara.T.Howard6](https://avatars.discourse-cdn.com/v4/letter/a/958977/32.png) [@Ara.T.Howard6](https://rubytalk.org/u/Ara.T.Howard6)\
**Post date:** [2 February 2006 19:39 UTC](https://rubytalk.org/t/chomping-and-stomping/24559/15 "2006-02-02T19:39:21Z")

</div>

golfing

&nbsp;&nbsp;&nbsp;def chomper() STDIN.detect{|x| x =~ /^qq/ or puts "hit me"} end

-a

> **···**
>
> On Fri, 3 Feb 2006, James Edward Gray II wrote:
> 
> > On Feb 2, 2006, at 11:59 AM, Jacob Fugal wrote:
> > 
> > > On 2/2/06, ara.t.howard@noaa.gov \<ara.t.howard@noaa.gov\> wrote:
> > > 
> > > > &nbsp;&nbsp;&nbsp;harp:~ \> ruby a.rb \< /dev/null  
> > > > &nbsp;&nbsp;&nbsp;a.rb:3:in `chomper': private method `chomp' called for nil:NilClass (NoMethodError)  
> > > > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;from a.rb:9
> > > > 
> > > > nil doesn't like that! 😉
> > > 
> > > Heh, yeah, I glossed over that too. You really need to check the  
> > > result of gets before you chomp it.
> > 
> > Isn't this why we have iterators in Ruby? We get to avoid all these messy loop ending tests...
> > 
> > > This is the way I'd write John's original loop (same semantics):
> > > 
> > > &nbsp;&nbsp;def chomper  
> > > &nbsp;&nbsp;&nbsp;&nbsp;while xx = gets  
> > > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;xx.chomp!  
> > > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;break if xx == 'qq'  
> > > &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;puts "hit me with a squirell!"  
> > > &nbsp;&nbsp;&nbsp;&nbsp;end  
> > > &nbsp;&nbsp;&nbsp;&nbsp;xx  
> > > &nbsp;&nbsp;end
> > 
> > def chomper  
> > $stdin.each do |line|  
> > &nbsp;&nbsp;&nbsp;line.chomp!
> > 
> > &nbsp;&nbsp;&nbsp;return line if line == "qq"
> > 
> > &nbsp;&nbsp;&nbsp;puts "Hit me with a squirrel!"  
> > end  
> > end
> 
> --  
> happiness is not something ready-made. it comes from your own actions.  
> - h.h. the 14th dali lama

---

<div class="post-metadata">

**Author:** ![Jacob\_Fugal](https://avatars.discourse-cdn.com/v4/letter/j/439d5e/32.png) [@Jacob\_Fugal](https://rubytalk.org/u/Jacob_Fugal)\
**Post date:** [2 February 2006 20:35 UTC](https://rubytalk.org/t/chomping-and-stomping/24559/16 "2006-02-02T20:35:33Z")

</div>

Because the original poster was asking for advice on why it wasn't  
working, not for a golfing contest.

Jacob Fugal

> **···**
>
> On 2/2/06, William James \<w\_a\_x\_man@yahoo.com\> wrote:
> 
> > Jacob Fugal wrote:  
> > \> PS. And let's not golf with this please...
> > 
> > If you don't like golf, why watch it?

---

<div class="post-metadata">

**Author:** ![W\_James](https://avatars.discourse-cdn.com/v4/letter/w/e274bd/32.png) [@W\_James](https://rubytalk.org/u/W_James)\
**Post date:** [2 February 2006 21:08 UTC](https://rubytalk.org/t/chomping-and-stomping/24559/17 "2006-02-02T21:08:17Z")

</div>

Jacob Fugal wrote:

> **···**
>
> > On 2/2/06, William James \<w\_a\_x\_man@yahoo.com\> wrote:  
> > \> Jacob Fugal wrote:  
> > \> \> PS. And let's not golf with this please...  
> > \>  
> > \> If you don't like golf, why watch it?
> > 
> > Because the original poster was asking for advice on why it wasn't  
> > working, not for a golfing contest.
> 
> The fact that his expectations were modest doesn't mean that  
> I shouldn't give him a bonus. One never has to ask for a golfing  
> contest, since those who enjoy programming and who test their  
> code before they post are always willing to indulge in that pastime.
