# How to be cool with map

**URL:** <https://www.ruby-forum.com/t/how-to-be-cool-with-map/112744>\
**Category:** Ruby\
**Created:** [August 22, 2007, 8:56pm UTC](https://www.ruby-forum.com/t/how-to-be-cool-with-map/112744 "2007-08-22T20:56:09Z")\
**Posts on this page:** 9\
**Page:** 1

<div class="post-metadata">

**Author:** ![Giles\_B](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/g/848f3c/32.png) [@Giles\_B](https://www.ruby-forum.com/u/Giles_B)\
**Post date:** [August 22, 2007, 8:56pm UTC](https://www.ruby-forum.com/t/how-to-be-cool-with-map/112744/1 "2007-08-22T20:56:09Z")

</div>

So I’ve got this file-checking script:

def check  
ok = true  
for\_every\_app do |app,app\_info|  
ok = File.exists?(app\_info[:root])  
end  
ok  
end

And it has a bug, which is that if it evaluates a good file after a  
bad file, it’ll return true for the whole list.

So here’s my suggested change:

def check  
ok = true  
for\_every\_app.values.each do |app\_info|  
ok = File.exists?(app\_info[:root]) if ok  
end  
ok  
end

Because if we have one false value, then the whole test is  
unnecessary. It’s basically like a short-circuit operator.

But I think there’s a better way to do it with map.

Something like

File.exists?(for\_every\_app.values.map{|x| x}

I think I’m way off, though. How do I get that right?

–  
Giles B.

Blog: [http://gilesbowkett.blogspot.com](http://gilesbowkett.blogspot.com)  
Portfolio: [http://www.gilesgoatboy.org](http://www.gilesgoatboy.org)  
Tumblelog: [http://giles.tumblr.com/](http://giles.tumblr.com/)

---

<div class="post-metadata">

**Author:** ![Giles\_B](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/g/848f3c/32.png) [@Giles\_B](https://www.ruby-forum.com/u/Giles_B)\
**Post date:** [August 22, 2007, 9:03pm UTC](https://www.ruby-forum.com/t/how-to-be-cool-with-map/112744/2 "2007-08-22T21:03:09Z")

</div>

Hi –

On Thu, 23 Aug 2007, Giles B. wrote:

> So I’ve got this file-checking script:
> 
> def check  
> ok = true  
> for\_every\_app do |app,app\_info|

Do you mean for there to be an .each in there?

> def check  
> But I think there’s a better way to do it with map.
> 
> Something like
> 
> File.exists?(for\_every\_app.values.map{|x| x}
> 
> I think I’m way off, though. How do I get that right?

You could do:

def check  
for\_every\_app.all? {|app,info| File.exists?(info[:root])}  
end

David

---

<div class="post-metadata">

**Author:** ![Giles\_B](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/g/848f3c/32.png) [@Giles\_B](https://www.ruby-forum.com/u/Giles_B)\
**Post date:** [August 22, 2007, 10:06pm UTC](https://www.ruby-forum.com/t/how-to-be-cool-with-map/112744/3 "2007-08-22T22:06:06Z")

</div>

Faster, because it breaks the loop as soon as possible, and  
less LOC:

def check  
for\_every\_app.values.find do |app\_info|  
not File.exists?(app\_info[:root])  
end ? false : true  
end

You may want to skip the “? false : true” part, but that breaks  
the encapsulation.

gegroet,  
Erik V. - [http://www.erikveen.dds.nl/](http://www.erikveen.dds.nl/)

---

<div class="post-metadata">

**Author:** ![Giles\_B](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/g/848f3c/32.png) [@Giles\_B](https://www.ruby-forum.com/u/Giles_B)\
**Post date:** [August 22, 2007, 10:52pm UTC](https://www.ruby-forum.com/t/how-to-be-cool-with-map/112744/4 "2007-08-22T22:52:13Z")

</div>

On Aug 22, 2:54 pm, “Giles B.” [removed\_email\_address@domain.invalid](mailto:removed_email_address@domain.invalid) wrote:

> And it has a bug, which is that if it evaluates a good file after a  
> end  
> I think I’m way off, though. How do I get that right?
> 
> –  
> Giles B.
> 
> Blog:[http://gilesbowkett.blogspot.com](http://gilesbowkett.blogspot.com)  
> Portfolio:[http://www.gilesgoatboy.org](http://www.gilesgoatboy.org)  
> Tumblelog:[http://giles.tumblr.com/](http://giles.tumblr.com/)

How about inject?

for\_every\_app.inject(true) {|good,x| good = File.exists?(x) if good}

---

<div class="post-metadata">

**Author:** ![Giles\_B](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/g/848f3c/32.png) [@Giles\_B](https://www.ruby-forum.com/u/Giles_B)\
**Post date:** [August 22, 2007, 10:43pm UTC](https://www.ruby-forum.com/t/how-to-be-cool-with-map/112744/5 "2007-08-22T22:43:10Z")

</div>

Alle mercoledì 22 agosto 2007, Erik V. ha scritto:

> the encapsulation.
> 
> gegroet,  
> Erik V. - [http://www.erikveen.dds.nl/](http://www.erikveen.dds.nl/)

This is shorter, and breaks as soon as a non-existing file is found

def check  
!for\_every\_app.values.any?{|f| !File.exist?(f)}  
end

Stefano

---

<div class="post-metadata">

**Author:** ![Giles\_B](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/g/848f3c/32.png) [@Giles\_B](https://www.ruby-forum.com/u/Giles_B)\
**Post date:** [August 22, 2007, 11:07pm UTC](https://www.ruby-forum.com/t/how-to-be-cool-with-map/112744/6 "2007-08-22T23:07:14Z")

</div>

Hi –

On Thu, 23 Aug 2007, Stefano C. wrote:

> > You may want to skip the “? false : true” part, but that breaks  
> > the encapsulation.
> > 
> > gegroet,  
> > Erik V. - [http://www.erikveen.dds.nl/](http://www.erikveen.dds.nl/)
> 
> This is shorter, and breaks as soon as a non-existing file is found
> 
> def check  
> !for\_every\_app.values.any?{|f| !File.exist?(f)}  
> end

You can save yourself the double negative:

for\_every\_app.values.all?{|f| File.exist?(f)}

And even save the creation of an intermediate array of values:

for\_every\_app.all?{|a,b| File.exist?(b)}

But I repeat myself 🙂 (See my earlier post.)

David

---

<div class="post-metadata">

**Author:** ![Giles\_B](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/g/848f3c/32.png) [@Giles\_B](https://www.ruby-forum.com/u/Giles_B)\
**Post date:** [August 22, 2007, 11:11pm UTC](https://www.ruby-forum.com/t/how-to-be-cool-with-map/112744/7 "2007-08-22T23:11:15Z")

</div>

On Aug 22, 4:34 pm, Kaldrenon [removed\_email\_address@domain.invalid](mailto:removed_email_address@domain.invalid) wrote:

> > ```
> > end
> > for_every_app.values.each do |app_info|
> > 
> > ```
> > 
> > Something like  
> > Tumblelog:[http://giles.tumblr.com/](http://giles.tumblr.com/)
> 
> How about inject?
> 
> for\_every\_app.inject(true) {|good,x| good = File.exists?(x) if good}

I guess this would be for\_every\_app.values.inject(true) {|good,x| good  
= File.exists?(x) if good}

But I think the idea was clear.

---

<div class="post-metadata">

**Author:** ![Giles\_B](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/g/848f3c/32.png) [@Giles\_B](https://www.ruby-forum.com/u/Giles_B)\
**Post date:** [August 23, 2007, 7:43pm UTC](https://www.ruby-forum.com/t/how-to-be-cool-with-map/112744/8 "2007-08-23T19:43:24Z")

</div>

On Aug 22, 2007, at 12:54 PM, Giles B. wrote:

> So I’ve got this file-checking script:
> 
> def check  
> ok = true  
> for\_every\_app do |app,app\_info|  
> ok = File.exists?(app\_info[:root])  
> end  
> ok  
> end

this sends alarm bells ringing to me. i would expect, from that  
small sample of code, that i could do

a\_ok = apps.all?{|app| app.info.root.exist?}

which is to say apps is a method or collection, an app knows it’s  
info, an info object knows it’s root, and that root is a Pathname  
object so therefore has an exist method. which would obviate the  
need for a method 😉

2cts.

a @ [http://drawohara.com/](http://drawohara.com/)

---

<div class="post-metadata">

**Author:** ![Giles\_B](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/g/848f3c/32.png) [@Giles\_B](https://www.ruby-forum.com/u/Giles_B)\
**Post date:** [August 22, 2007, 11:36pm UTC](https://www.ruby-forum.com/t/how-to-be-cool-with-map/112744/9 "2007-08-22T23:36:20Z")

</div>

Alle mercoledì 22 agosto 2007, David A. Black ha scritto:

> David

You’re right. Somehow, I thought that all? needed to iterate over all  
the  
values and any? didn’t. Of course, now I realized that, just as any?  
will  
stop at the first positive result, all? will stop at the first negative  
result.

Stefano
