Ruby:悪い部分[終了]


20

私は最近、Crockfordの本「Javascript:The Good Parts」を読みましたが、基礎となる前提の1つは、プログラミング言語にはプログラマが避けるべき悪い機能セットがある可能性があることです。

私はルビイストであり、言語が大好きである一方、視点を得るには常に価値があります。それでは、Rubyで最悪の機能(メソッド、クラス、プラクティスなど)とは何だと思いますか?ここでの私の意図は、言語自体の長所や速度などについて議論を始めることではありません。むしろ、過去の経験に基づいて、使用するのに危険/厄介/苦痛と思われる機能についての議論を希望します。


1
私は「終わり」という言葉を使わなければならないというファンではありませんでしたが、それと「{」および「}」との混合はさらに面倒になります。Pythonスタイルの構文か、まっすぐな{&}のどちらかに感謝します。この点については議論の余地がありますが、最終的には個人の好みに大きく関係しています。RubyがPythonとPerlの最もgliい部分をまとめてまとめると言う人がいるのを聞きました。ただし、Rubyの学習を楽しんでいます。

私は実際にこの質問がとても好きで、答えを楽しみにしていますが、それでもそれを閉じることに投票しました。Stack Overflowに適しているとは思わない(潜在的に主観的/議論的すぎたり、無制限であるなどの理由で)。
stakx

避けるべき危険な行為を明らかにする可能性があるので、議論する価値があると思います。私はあなたの主張を見て、質問をより狭くなるように編集しました。

9
この質問がどのように明確に区別されているかわかりません。たとえば、Ruby言語で改善したいことは何ですか?初心者に警告するべきRuby Gotchaとは何ですか?Rubyの実際の問題は何ですか?またはRubyの問題点に関する他の膨大な質問。でもプラス、場合、この質問は、それらの他のものとの差別化を進化さ、それは上属しますProgrammers.SE、ないのStackOverflow。
ヨルグWミットタグ

2
目をチェックする必要があります。この質問のタイトルは「Ruby:The Brad Pitts」だと思いました。
oosterwal

回答:


8

あなたは見なければならない死にAバトル:Rubyの対Pythonのがゲイリー・ベルナールで。彼は引用する:

私がRubyで見苦しいと感じるのは、RSpecのような素晴らしいRubyソフトウェアを可能にするものであり、そのPythonは(現在の実装を考えれば)決してありえないことです。

彼は特にPythonについて多くのことを語っていますが、Rubyの奇妙な多くのことに触れています。大きな包括的な主題の1つは、サルのパッチングです。

Rubyオブジェクト(他のオブジェクト指向言語のオブジェクトとは異なります)は個別に変更できます。オブジェクトごとにいつでもメソッドを追加できます。Rubyでは、オブジェクトの動作または機能は、クラスによって提供されるものとは異なる場合があります。

これは多くの柔軟性を提供し、Rubyの最も人気のある複雑なgemの一部を強化しますが、どこかのライブラリがコアメソッドを変更したことを認識せずに問題をデバッグしようとすると、お尻に噛みつきます。


Javascriptを使用すると、オブジェクトを同様に扱うことができます。
0112 14年

8

一部の人々はレール上のルビーの観点からのみルビーを考えていますが、言語がそれ自身でかなりよく立っているので、それはちょっと迷惑です。


7

最悪の機能はopen classes、変更されたクラスの現在および将来のすべてのインスタンスの動作をグローバルに変更できることだと思います。

この機能の問題のある部分は、Rubyインタープリターが定義を見つけたときに実行時にこれらの(グローバル)変更が発生することです。これは、動作を突然変更するいくつかのオブジェクトを既にインスタンス化してからかなり後になります。

大きなコードベースでは、これは非常に非常に難しいバグを見つける可能性があります-特にこれはRubyの弱い(たとえばCLRまたはJVMと比較して)デバッグストーリーとevalこのコンテキストの他の機能(たとえば)の使用により悪化するためこのグローバルな変化が発生した場所を見つけるのは非常に困難です。すなわち、トラブルを引き起こしている「正しい」クラスが疑われるポイントにすでに到達している場合!私の経験では、実際の犯人を使用してオブジェクトで問題が表面化し始めるので、通常は野生のガチョウの追跡から始めます。

したがって、最良の方法は、オープンクラスの使用を停止する#extendこと(および変更をaに配置することModuleは、より安全で、理解しやすく、テストしやすいことです)、または回避できない場合:

  • 新しい動作でクラスを拡張するだけです(つまり、既存の動作をオーバーライドしません)
  • ソースコードツリーに定義済みの場所があり、オープンクラスを使用するすべての拡張機能を配置する必要がある
  • #eval友達を使ってオープンクラスを作成しないでください
  • オープンクラスのすべての使用法を、すべての開発者が見ることができる大きな目に見えるチャートに配置します-そして、それらの変更は、コードベース全体(彼らが行う)に影響する「アーキテクチャ上の決定」であり、クイックハックの場所ではないことを明確にします現在のタスクのために

5

私がルビーを使わない最大の理由:氷河期の北極での1月の糖蜜より遅い。言語のベンチマークは不正確な科学ですが、RubyはJavaScriptやPythonよりも大幅に遅いようです。


それも私の経験でした。
チャックステファン

2
あなたが開発したアプリケーションはどのルビーに対して遅すぎましたか?つまり、遅いと言うとあなたを信じますが、どうして目標に到達するのを止めましたか?
デビッド

1
プロトタイプのようなものを作りたいと思っているとき、Rubyは素晴らしいと思います。それは巨大ではなく、大量の計算を行わないものです。多くのCPUサイクルを絶えず噛んでいると予想される場合、優秀なプログラマーなら誰でもCやC ++のようなものを使用することを知っています。
ジェフウェリング

1
@David:単純なDNAシーケンス処理コードにRubyを使用することを検討しますが、Pythonが同様のニッチを満たし、同様の機能を持ち、はるかに高速であるため、そうしません。より低いレベルに進んでも構わないのであれば、Dはさらに高速で便利です。
dsimcha

1
@Jeff:同意しましたが、CとC ++を書くのは苦痛です。Rubyのような高レベル言語のポイントは、この苦痛をできる限り避けることです。それらが遅いほど、彼らはこの目標をうまく達成できません。Rubyは、高レベルの動的言語であっても低速です。それとNumPy / SciPyが、高レベルの動的言語が必要なときにPythonを代わりに使用する理由です。
dsimcha

4

これをRuby on Railsに拡張できる場合、次のようにします。

  1. データベースロジックによって、すべてのテーブルにauto_incrementプライマリキーが与えられているという事実は、それらを必要とせず、持つべきではないテーブルも含みます。

  2. 複合キーがまったくサポートされていないという事実。

単純なRubyの場合、私の不満は、表現力と安全性を犠牲にする他の言語と同じです。ほんの少しのコードで多くのことをするのは簡単ですが、どんな量のコードでも巨大な混乱を作るのは同じくらい簡単です。


質問の範囲を狭めた編集内容をご覧ください。編集に関するこの質問が承認された場合は、Railsについても別の並列タスクを開始します。

1
Railsアプリのすべてのテーブルにauto_incrementID が必要なわけではありません。特にhas_and_belongs_to_many関係のテーブルを結合する場合は、id列を明示的に持たないことをお勧めします。
ブレットベンダー

@Brett-これらの比較的新しい追加はありますか?私が2008年の初めにそれで遊んでいたとき、それは間違いなくそれらの機能を持っていなかった。いずれにせよ、それらが現在利用可能であることは素晴らしいことです。

1
@aroth:他の誰もが「比較的新しい」とは「過去3年以内」を意味すると考えるかどうかはわかりません:

DataMapperと呼ばれるRailsのActiveRecordに代わるものがありますが、これはActiveRecord ほどではありません。
エンディチャジョノ

3

Rubyは、メタプログラミング(リフレクション、イントロスペクション)、マルチパラダイムプログラミング、およびダイナミズムを一般的でないレベルで採用しています。パワーと柔軟性を備えた足で自分を撃つのは簡単です。

面倒?Rubyには、非常に読みやすい、または中断できない機能があります。Bashスクリプトに属しているように見えるコードを見てきました。

悪い習慣?知恵よりも賢明さを重視するRubyistもいます。彼らは自分の賢さを示すトリックを書いて共有していますが、これは読みにくくて壊れやすいコードを作成します。

余談ですが、Javascriptは設計上災害でした。「The Good Parts」の本は、その隠された美しさを抽出しようとしています。「それを行うには複数の方法があります」(つまり、柔軟性)を普及させた言語であるPerlには、「Perl、Best Practices」に似た本があります。Perlの歴史は実験の1つであり、経験を積んだ経験があり、「ベストプラクティス」はその知識を表しています。Perl 6は、その知識などに基づいて言語を再起動することになると思います。Rubyも同様の問題に苦しむ可能性があります。

@Jamesとforループ... ruby​​でforループを実行すると、「。each」が呼び出されます。したがって、「for」は、Cスタイルのループに慣れている人にとっては構文上の砂糖です。しかし、Rubyistとしては、常に.map、.inject、.each_with_objectなどのイテレーターを使用します。rubyで "i = 0; i> 6; i ++"のようなforループを記述する必要は決してないので、習慣を落とすことになります。@andrew ...雄弁なルビーはループを支持しません。


-1

これは言語よりもプログラマーのことですが、Rubyプログラマーがループを嫌うのはなぜですか?

Rubyには次の特徴があります。

someCollection.each do |item|
   ...
end

しかし、forループがまったく同じことをしない状況で使用されるのを見たことはありません。

私は何度か尋ねましたが、これに対する良い答えは一度もありませんでした。

それが単なるスタイルのことなら、私はそれを受け入れてうれしいですが、Rubyプログラマーがこれについて本当にうまくいくのを見て、本当に興味があります。


1
「キーを押す回数が少ない」という答えも得られましたが、これは明らかに間違っています... :
ジェームズ

2
2つの理論:1)forループの使用は、n00bsが行うことです。RubyでCをプログラミングしている人々。2)Rubyではブロックが頻繁に使用されるため、ブロックに似ていないものを使用することは精神的な労力の増加にすぎません。
アンドリューグリム

3
Rubyを学び始めたばかりですが、ブロックはPythonを使用しようとするときに本当に好きで見逃しているものです。forループも同じことをしますか?もちろん、私にとって、この種のスタイルはforループよりも私の好みに合っています。
ジェッティ

2
@andrew正直に言うと、あなたの最初の答えは、私が前に尋ねたときに戻ってきた種類のゴミです。本当の理由はありません。微妙なin辱があります。@ウェイン、@ジェッティ、@アンドリュースの2番目の回答:ありがとう。それでは結構です。
ジェームズ

1
ループの「拡張」を意味する場合(別名:<式>の<値> do ...)#eachが使用されており、外観が一般的に使用されているいとこ#inject、#collect、#に近いこと以外に違いはありません。リジェクトなど。「C」スタイルのインデックス付きループ(別名、for int i = 0; i <なんでも; ++ i)について話している場合、違いは、a)「off by one」エラーは不可能、b)ループの意図が明確になること-#eachの意味は「各要素に対して副作用が生じる」ことです。forループでは、ループの目的を把握するためにループ全体を読む必要があります。
アレクサンダーバッティスティ

-1

他の言語との後方互換性のためだけに追加されたものは、通常避けたいと思います。たとえば、Perlismsおよびfor x in y


私はRubyのプログラマ程度とループのための答えを掲示し、あなたが説明できる場合、私は感謝されると思います:-)
ジェームズ・
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.