2012-02-22 22 views
6

Trong ruby, tôi bắt đầu thấy một thực tế khá bình thường bao gồm các mô-đun và mixins được tham chiếu như :: ModuleName :: ClassName, trong quá khứ nó đã được khá nhiều chỉ là ModuleName :: ClassName.Sự khác nhau trong :: ModuleName :: ClassName và ModuleName :: ClassName

Điều tôi muốn đạt được ở đây là hiểu biết tốt về lý do tại sao thực tiễn này được xem gần đây hơn và những gì nó thực hiện khác đi.

Sự khác biệt là gì?

Lợi ích gì (nếu trước đó không trả lời câu hỏi này)?

Cảm ơn bạn đã nhập trước.

Trả lời

9

Nếu bạn đặt :: khi bắt đầu, bạn đang tham chiếu đến không gian tên chung, nếu bạn không tham chiếu đến không gian tên hiện tại của mình.

Thông thường nếu bạn không có lớp/mô-đun có cùng tên trong lớp học/mô-đun, bạn sẽ không cần sử dụng số :: ngay từ đầu.

class Customer 

    def to_s 
    "Customer global" 
    end 

end 


class Order 

    class Customer 
    def to_s 
     "Customer within order" 
    end 
    end 


    def initialize 
    puts Customer.new 
    puts ::Customer.new 
    end 


end 

Order.new 

sẽ in ra

Customer within order 
Customer global 
+0

+1 để có giải thích tuyệt vời với một ví dụ đơn giản. – nkm

2

Khi bạn làm ::ModuleName::ClassName bạn đang nói:

tôi muốn bạn tìm kiếm ::ModuleName::ClassName tại namespace gốc, bỏ qua nếu mã này được tìm thấy bên trong một mô-đun khác. Vì vậy, nó sẽ luôn luôn tìm kiếm một lớp học đó là đặt tên như ::ModuleName::ClassName và không có gì khác

Khi bạn nói nó như ModuleName::ClassName này, bạn đang nói:

tôi muốn bạn tìm kiếm ModuleName::ClassName nhưng nhìn ở phạm vi hiện tại trước và sau đó ở các phạm vi khác. Vì vậy, nếu bạn có một mô-đun gọi là MyModule và tham chiếu mô-đun của tôi ModuleName::ClassName thì trước tiên hãy thử tìm MyModule::ModuleName::ClassName rồi cố gắng giải quyết ::ModuleName::ClassName.

Khi tôi xác định mã như thế này, tôi hầu như luôn sử dụng :: ModuleName :: ClassName để tránh bất kỳ xung đột đặt tên nào.

+0

Thú vị, vì vậy tôi đoán rằng bạn có thể sử dụng nó theo một trong hai cách. Sử dụng :: để xác minh bạn không có vấn đề đặt tên và không sử dụng gì nếu có tình huống sẽ gây xung đột đặt tên? Hoặc bạn sẽ vào thời điểm đó, đổi tên một lớp học? –

+0

Điều đó phụ thuộc, đôi khi bạn có một plugin hoặc đá quý có cùng tên với lớp của bạn (tôi đã thấy điều này xảy ra với đá quý actions_as_taggable) và tôi đã kết thúc đổi tên mô hình của mình. Ngày nay tôi luôn sử dụng :: khi sử dụng các lớp không gian tên và tôi luôn định nghĩa các lớp của mình với lớp ** SomeModule :: SomeClass; kết thúc ** thay vì ** mô-đun SomeModule; lớp SomeClass; kết thúc ; kết thúc**. Cuối cùng, nó trở nên đơn giản hơn nhiều để tìm kiếm một lớp bằng tên đầy đủ của nó. –

Các vấn đề liên quan