रूबी: आत्म विस्तार


113

रूबी में, मैं के मूल विचार को समझता हूं extend। हालाँकि, कोड के इस सेगमेंट में क्या हो रहा है? विशेष रूप से, क्या करता extendहै? क्या यह उदाहरण तरीकों को वर्ग विधियों में बनाने का एक सुविधाजनक तरीका है? आप शुरुआत से ही कक्षा के तरीकों को निर्दिष्ट करने के बजाय इसे इस तरह क्यों करेंगे?

module Rake
  include Test::Unit::Assertions

  def run_tests # etc.
  end

  # what does the next line do?
  extend self
end

जवाबों:


115

यह उदाहरण के तौर तरीकों को वर्ग विधियों में बनाने का एक सुविधाजनक तरीका है। लेकिन आप इसे एक अधिक कुशल सिंगलटन के रूप में भी उपयोग कर सकते हैं ।


2
उस तरह का सिंगलटन अधिक कुशल क्यों है?
xuuso

5
आपके लिंक ने मेरे दोस्त को सड़ा दिया है।
यूलसीज़ बीएन


1
यह उत्तर अपर्याप्त है क्योंकि यह नहीं समझाता है कि कैसे प्रश्न में कीवर्ड उदाहरण तरीके को वर्ग विधियों में बनाता है। यह भी स्पष्ट नहीं करता है कि 'अधिक कुशल सिंगलटन' क्या है, या extend selfइसके साथ क्या करना है।
जयेकी

29

एक मॉड्यूल में, स्वयं एक मॉड्यूल वर्ग है। इसलिए उदाहरण के लिए

puts self

वापसी करेंगे रेक,

extend self

मूल रूप से Rake में परिभाषित उदाहरण विधियाँ उपलब्ध हैं, जिससे आप कर सकते हैं

Rake.run_tests

23

मेरे लिए यह हमेशा के बारे में सोच में मदद करता है extendके रूप में includeसिंगलटन वर्ग (भी मेटा या eigen वर्ग के रूप में जाना जाता है) के अंदर।

आप शायद जानते हैं कि सिंगलटन क्लास के अंदर परिभाषित तरीके मूल रूप से क्लास के तरीके हैं:

module A
  class << self
    def x
      puts 'x'
    end
  end
end

A.x #=> 'x'

अब जब हम जानते हैं कि, एकल वर्ग के अंदर मॉड्यूल में विधियां extendहोंगी includeऔर इस प्रकार उन्हें वर्ग विधियों के रूप में उजागर किया जाएगा:

module A
  class << self
    include A

    def x
      puts 'x'
    end
  end

  def y
    puts 'y'
  end
end

A.x #=> 'x'
A.y #=> 'y'

15

लिंक रोट से बचने के लिए, उपयोगकर्ता के द्वारा पोस्ट की गई क्रिस वानस्ट्रथ की ब्लॉग पोस्ट को नीचे पोस्ट किया गया है (उसकी अनुमति से)। फिर भी, कुछ भी एक मूल धड़कता नहीं है, इसलिए जब तक यह काम करना जारी रखता है, तब तक उसके लिंक का उपयोग करें।


→ सिंगिन के सिंगलेट्स 18 नवंबर 2008 में वह सामान है जो मुझे अभी समझ नहीं आया है। उदाहरण के लिए, डेविड बोवी। या दक्षिणी गोलार्ध। लेकिन रूबी के सिंगलटन की तरह कुछ भी मेरे दिमाग में नहीं आया। क्योंकि वास्तव में, यह पूरी तरह से अनावश्यक है।

यहाँ वे आपके कोड के साथ क्या करना चाहते हैं:

require 'net/http'

# first you setup your singleton
class Cheat
  include Singleton

  def initialize
    @host = 'http://cheat.errtheblog.com/'
    @http = Net::HTTP.start(URI.parse(@host).host)
  end


  def sheet(name)
    @http.get("/s/#{name}").body
  end
end

# then you use it
Cheat.instance.sheet 'migrations'
Cheat.instance.sheet 'yahoo_ceo'

लेकिन वह पागल है। सत्ता से लड़ना।

require 'net/http'

# here's how we roll
module Cheat
  extend self

  def host
    @host ||= 'http://cheat.errtheblog.com/'
  end

  def http
    @http ||= Net::HTTP.start(URI.parse(host).host)
  end

  def sheet(name)
    http.get("/s/#{name}").body
  end
end

# then you use it
Cheat.sheet 'migrations'
Cheat.sheet 'singletons'

कोई भी क्यों नहीं? एपीआई अधिक संक्षिप्त है, कोड का परीक्षण, मॉक और स्टब करना आसान है, और एक उचित वर्ग में परिवर्तित करने के लिए अभी भी मृत सरल है आवश्यकता उत्पन्न होनी चाहिए।

((कॉपीराइट दस क्रिस वानस्ट्रथ चाहिए))


लिंकरोट से बचने का एक और तरीका है कि वेबैकबैक मशीन - web.archive.org जैसी किसी चीज़ का उपयोग किया जाए - यह पूरे वेब पेजों का इतिहास रखता है, मैंने इसे वैसे भी लिंकरोट के कई मामलों में काफी मददगार पाया है।
केम मेसन

3

extend selfमॉड्यूल विधियों के रूप में सभी मौजूदा उदाहरण विधियाँ शामिल हैं। यह कहने के बराबर है extend RakeRakeवर्ग की एक वस्तु भी है Module

समकक्ष व्यवहार को प्राप्त करने का दूसरा तरीका होगा:

module Rake
  include Test::Unit::Assertions

  def run_tests # etc.
  end

end 

Rake.extend(Rake)

यह निजी तरीकों के साथ स्व-निहित मॉड्यूल को परिभाषित करने के लिए इस्तेमाल किया जा सकता है।

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.