Unfortunately most professional Ruby work is still done within the Rails framework these days, which more or less binds you to a more traditional OO type style. I do find that in regards to everything other than class/object abstraction my coding style gets more and more functional.
Especially when working in a team environment though it's important to stick to some established standards and idioms...
That said, Ruby itself gets more functional with each release, but it would seem unlikely that it'll ever completely shed it's OO-ness.
The python code here is not very idiomatic. Better would be something like:
import re
with open('companies') as f:
important_companies = set(f)
articles = ['article1.md', 'article2.md', 'article3.md']
http_regex = re.compile(r"https?:\/\/(\w+)?(\.(\w+))*\.(com|org|net)")
def parse_article(a):
with open(a, 'r') as f:
words = f.read().split()
urls = (http_regex.search(w) for w in words)
companies = (match.group(0).capitalize() for match in urls if match)
return (c for c in companies if c in important_companies)
[c for a in articles for c in parse_article(a)]
(Note, I didn’t test this; I might be slightly misunderstanding some of what the code is supposed to do; the basic idea should be clear though. I think the original Python code posted might be broken: a regexp match object shouldn’t be directly subscriptable, it’s not clear why he’s opening the file 'atp' for each article, and I’m really not sure what’s supposed to happen when the url regexp doesn’t match. One nice thing to notice: in Python a file object can be iterated over, and will spit out its lines; passing a file into list() or set() will turn its lines into the appropriate data structure. But if explicit splitting is ever necessary, the author should use foo.splitlines() rather than foo.split('\n'). Finally, compiling a regexp for each word in every file is bad form, and he should really be using "raw" strings for regexps. My guess is that the Python code in the original article was never actually tested.)
Or even better, use a generator:
import re
with open('companies') as f:
important_companies = set(f)
articles = ['article1.md', 'article2.md', 'article3.md']
http_regex = re.compile(r"https?:\/\/(\w+)?(\.(\w+))*\.(com|org|net)")
def parse_article(a):
with open(a, 'r') as f:
for word in f.read().split():
url = http_regex.search(word)
if url:
name = url.group(0).capitalize()
if name in important_companies:
yield name
[c for a in articles for c in parse_article(a)]
In my opinion, either of these, but especially the second, makes control flow much much clearer than either the ruby or python examples in the original article.
I'm not a fan of if statements (especially nested) or for loops (except for side effects), which is why I coded like I did — in the style of a Lisp. That said, thanks for the excellent code. I'm going to look it over.
I'll go back tomorrow and double-check the regex. I'm definitely not an expert with those objects in Python.
This is a terrible read. This is a rant about what the author is used to, and anything else is different and hard.
Now, in my mind, these method names are decidedly ugly. They aren’t friendly, short, clean, straightforward or simple. I don’t think anyone would argue with me there. Certainly no one’s actually happy typing the extra underscores.
That’s true, function passing is painless in Python and a little harder in Ruby. But coll.map &f isn’t so bad, and for me, it’s definitely not a deal breaker. I’ve actually gotten used to it. To me, the extra syntax is the price we pay for internal consistency.
These two quotes above are on one hand poopooing some apparently arbitrary naming convention in python and then praising the same kind of apparently arbitrary syntax quirk in ruby.
(I find the double prefixing and suffixing underscores to make sense in python: these methods are called implicitly by other constructs, never called directly.)
Maybe rant was too strong of a word, but I don't think there much meat to this write up, because there isn't much introspection into why any of these differences are the way they are, it's mainly just pointing them out and favoring one over the other based on familiarity.
9 comments
[ 4.3 ms ] story [ 30.4 ms ] threadEspecially when working in a team environment though it's important to stick to some established standards and idioms...
That said, Ruby itself gets more functional with each release, but it would seem unlikely that it'll ever completely shed it's OO-ness.
Rambling aside, some great links.
http://moonbase.rydia.net/mental/writings/programming/monads...
http://www.khelll.com/blog/ruby/ruby-currying/
http://nex-3.com/posts/43-fun-with-the-y-combinator-in-ruby
It's a family of functions: http://en.wikipedia.org/wiki/Indexed_family
Or even better, use a generator:
In my opinion, either of these, but especially the second, makes control flow much much clearer than either the ruby or python examples in the original article.I'll go back tomorrow and double-check the regex. I'm definitely not an expert with those objects in Python.
Now, in my mind, these method names are decidedly ugly. They aren’t friendly, short, clean, straightforward or simple. I don’t think anyone would argue with me there. Certainly no one’s actually happy typing the extra underscores.
That’s true, function passing is painless in Python and a little harder in Ruby. But coll.map &f isn’t so bad, and for me, it’s definitely not a deal breaker. I’ve actually gotten used to it. To me, the extra syntax is the price we pay for internal consistency.
These two quotes above are on one hand poopooing some apparently arbitrary naming convention in python and then praising the same kind of apparently arbitrary syntax quirk in ruby.
(I find the double prefixing and suffixing underscores to make sense in python: these methods are called implicitly by other constructs, never called directly.)