PythonとRubyの議論はたくさんありますが、機能Xが言語Yを吸う理由、または言語YにXがないのに実際にはそうだと主張している理由がすべて逆転するため、私はそれらすべてがまったく役に立たないと思います。また、なぜPythonを好むのかについても正確に理解していますが、これは主観的なものであり、開発の趣味が私とは異なる可能性があるため、誰もが選択する助けにはなりません。
したがって、違いを客観的にリストすることは興味深いことです。したがって、「Pythonのラムダは最悪」ではありません。代わりに、PythonができないことをRubyのラムダができることを説明してください。主観なし。サンプルコードは良いです!
1つの回答にいくつかの違いがないようにしてください。そして、あなたが知っているものは正しいものに投票し、あなたが知っているものは間違っている(または主観的である)ものに投票してください。また、構文の違いは興味深いものではありません。Pythonはインデントを使用して、Rubyが角かっこで終了するのと同じように動作し、@はPythonではselfと呼ばれます。
更新:これはコミュニティWikiになりましたので、ここで大きな違いを追加できます。
Rubyのクラス本体にはクラス参照があります
Rubyでは、クラス本体にすでにクラス(自己)への参照があります。Pythonでは、クラスの構築が完了するまで、クラスへの参照はありません。
例:
class Kaka
puts self
end
この場合のselfはクラスであり、このコードは「カカ」を出力します。クラス名を出力したり、他の方法でPythonのクラス定義本体(メソッド定義の外部)からクラスにアクセスしたりする方法はありません。
Rubyではすべてのクラスが変更可能です
これにより、コアクラスの拡張機能を開発できます。以下は、レール拡張の例です。
class String
def starts_with?(other)
head = self[0, other.length]
head == other
end
end
Python(''.startswith
メソッドがなかったと想像してください):
def starts_with(s, prefix):
return s[:len(prefix)] == prefix
(文字列だけでなく)任意のシーケンスで使用できます。これを使用するには、明示的にインポートする必要があります(例:)from some_module import starts_with
。
RubyにはPerlのようなスクリプト機能があります
Rubyには、ファーストクラスの正規表現、$変数、awk / perlの行ごとの入力ループ、その他の機能があり、テキストファイルを変更したり、他のプログラムのグルーコードとして機能する小さなシェルスクリプトを作成するのに適しています。
Rubyはファーストクラスの継続を持っています
callccステートメントに感謝します。Pythonでは、さまざまな手法で継続を作成できますが、言語に組み込まれたサポートはありません。
Rubyにはブロックがあります
「do」ステートメントを使用すると、Rubyで複数行の無名関数を作成できます。この関数は、引数としてdoの前のメソッドに渡され、そこから呼び出されます。Pythonでは、代わりにメソッドを渡すか、ジェネレータを使用してこれを行います。
ルビー:
amethod { |here|
many=lines+of+code
goes(here)
}
Python(RubyブロックはPythonのさまざまな構成に対応しています):
with amethod() as here: # `amethod() is a context manager
many=lines+of+code
goes(here)
または
for here in amethod(): # `amethod()` is an iterable
many=lines+of+code
goes(here)
または
def function(here):
many=lines+of+code
goes(here)
amethod(function) # `function` is a callback
興味深いことに、ブロックを呼び出すためのRubyの便利なステートメントは「yield」と呼ばれ、Pythonではジェネレーターを作成します。
ルビー:
def themethod
yield 5
end
themethod do |foo|
puts foo
end
Python:
def themethod():
yield 5
for foo in themethod():
print foo
原則は異なりますが、結果は驚くほど似ています。
Rubyは関数型(パイプのような)プログラミングをより簡単にサポートします
myList.map(&:description).reject(&:empty?).join("\n")
Python:
descriptions = (f.description() for f in mylist)
"\n".join(filter(len, descriptions))
Pythonには組み込みジェネレーターがあります(上記のように、Rubyブロックのように使用されます)。
Pythonは、言語のジェネレーターをサポートしています。Ruby 1.8では、継続を使用してブロックからジェネレーターを作成するジェネレーターモジュールを使用できます。または、block / proc / lambdaを使用することもできます。さらに、Ruby 1.9では、ファイバーはジェネレーターであり、ジェネレーターとしても使用できます。Enumeratorクラスは組み込みジェネレーターです4
docs.python.orgには、このジェネレーターの例があります。
def reverse(data):
for index in range(len(data)-1, -1, -1):
yield data[index]
これを上記のブロックの例と比較してください。
Pythonには柔軟な名前空間処理があります
Rubyでは、でファイルをインポートするとrequire
、そのファイルで定義されたすべてのものが最終的にグローバルネームスペースになります。これは名前空間の汚染を引き起こします。その解決策はRubyモジュールです。ただし、モジュールで名前空間を作成する場合は、その名前空間を使用して、含まれているクラスにアクセスする必要があります。
Pythonでは、ファイルはモジュールであり、含まれている名前をfrom themodule import *
でインポートして、必要に応じて名前空間を汚染することができます。ただし、を使用して選択した名前だけをインポートしfrom themodule import aname, another
たりimport themodule
、を使用して名前にアクセスしたりすることもできますthemodule.aname
。名前空間のレベルを増やしたい場合は、モジュールと__init__.py
ファイルを含むディレクトリであるパッケージを使用できます。
Pythonにはドキュメント文字列があります
docstringは、モジュール、関数、メソッドにアタッチされ、実行時にイントロスペクトできる文字列です。これは、helpコマンドや自動ドキュメンテーションなどの作成に役立ちます。
def frobnicate(bar):
"""frobnicate takes a bar and frobnicates it
>>> bar = Bar()
>>> bar.is_frobnicated()
False
>>> frobnicate(bar)
>>> bar.is_frobnicated()
True
"""
Rubyに相当するものはjavadocsに似ており、メソッド内ではなくメソッドの上にあります。これらは、1.9のMethod#source_locationの使用例を使用して、実行時にファイルから取得できます。
Pythonには多重継承があります
Rubyはそうではありません(「意図的」-RubyのWebサイトを参照してください。Rubyでの実行方法についてはこちらを参照してください)モジュールの概念を一種の抽象クラスとして再利用します。
Pythonにはリスト/辞書内包表記があります
Python:
res = [x*x for x in range(1, 10)]
ルビー:
res = (0..9).map { |x| x * x }
Python:
>>> (x*x for x in range(10))
<generator object <genexpr> at 0xb7c1ccd4>
>>> list(_)
[0, 1, 4, 9, 16, 25, 36, 49, 64, 81]
ルビー:
p = proc { |x| x * x }
(0..9).map(&p)
Python 2.7以降:
>>> {x:str(y*y) for x,y in {1:2, 3:4}.items()}
{1: '4', 3: '16'}
ルビー:
>> Hash[{1=>2, 3=>4}.map{|x,y| [x,(y*y).to_s]}]
=> {1=>"4", 3=>"16"}
Pythonにはデコレータがあります
Rubyでデコレーターに似たものを作成することもできます。また、デコレーターはPythonほど必要ではないと主張することもできます。
構文の違い
Rubyでは、すべてのスコープを閉じるために「end」または「}」が必要ですが、Pythonは空白のみを使用します。Rubyで空白のみのインデントを許可する試みが最近行われましたhttp://github.com/michaeledgar/seamless