我在名为my_module.rb的文件中有一个Ruby模块:
module My_module
def my_module_method
puts 'inside my method'
end
end
在同一文件夹中的文件my_class.rb中,我有一个包含在模块中的类。
module My_module
class My_class
def my_object_method
My_module.my_module_method
end
end
end
My_module::My_class.new.my_object_method => 'undefined method 'my_module_method''
我没想到会出现这个错误。我假设Ruby会遇到'My_module.my_module_method'这一行并搜索一个名为'My_module'的模块,并在其中搜索一个名为'my_module_method'的方法。例如,这就是Java所做的。但是,Ruby不会这样做。为了让my_object_method工作,我必须在my_class.rb中写:
require 'my_module.rb'
为什么Ruby在调用my_object_method时没有搜索My_module?它似乎很明显应该搜索什么,因此需要程序员明确地写'是的,Ruby,请允许我调用模块范围的方法。我错过了什么?
答案 0 :(得分:1)
Ruby不会自动加载文件。如果您需要某个文件中的代码,则必须明确加载它(通过调用require)。
因此,当您运行“ruby my_class.rb”时,它只加载此文件,您必须自己定义文件之间的依赖关系。
答案 1 :(得分:0)
您似乎对如何定义类方法有误解。为了使您的方法调用有效,您可以将其定义为 > test <-data.table(id = c(1,1,2,3,4,5,5), type = c("a","b","a","c","a","a","b"),
+ date = c("2017-08-01", "2017-08-05", "2017-08-01",
+ "2017-08-01", "2017-08-02", "2017-08-03", "2017-08-04"))
> test
id type date
1: 1 a 2017-08-01
2: 1 b 2017-08-05
3: 2 a 2017-08-01
4: 3 c 2017-08-01
5: 4 a 2017-08-02
6: 5 a 2017-08-03
7: 5 b 2017-08-04
> test[type == "a",temp_date := date]
> test
id type date temp_date
1: 1 a 2017-08-01 2017-08-01
2: 1 b 2017-08-05 NA
3: 2 a 2017-08-01 2017-08-01
4: 3 c 2017-08-01 NA
5: 4 a 2017-08-02 2017-08-02
6: 5 a 2017-08-03 2017-08-03
7: 5 b 2017-08-04 NA
> test[, a_date := first(temp_date), by = c("id")]
id type date temp_date a_date
1: 1 a 2017-08-01 2017-08-01 2017-08-01
2: 1 b 2017-08-05 NA 2017-08-01
3: 2 a 2017-08-01 2017-08-01 2017-08-01
4: 3 c 2017-08-01 NA NA
5: 4 a 2017-08-02 2017-08-02 2017-08-02
6: 5 a 2017-08-03 2017-08-03 2017-08-03
7: 5 b 2017-08-04 NA 2017-08-03
。
在类和模块中,当使用def self.my_method_name
或self.
语法将方法定义为类方法时,方法的工作方式相同。但是,在这两种情况下,实例方法(没有class << self
的方法)的工作方式不同。在课程中,正如您似乎理解的那样,一旦您使用self.
实例化课程,它们就可以访问。在模块中,只有.new
或include
才能访问这些模块。
另见:
difference between class method , instance method , instance variable , class variable?
http://www.rortuts.com/ruby/ruby-include-vs-extend/
哦顺便说一下。 Ruby没有强制执行任何每个类有1个文件(相同名称)的约定。您需要在任何需要的地方手动要求文件。虽然有一些框架,如Rails自动需要文件,并强制命名约定。