为什么 Rails' attr_getter 实际上是多余的
Why Rails' attr_getter is actually redundant
我正在 Rails' attr_accessor 上学习 Ruby 的实际功能。在下面的示例中,我知道它将生成“name”和“name=”方法。其中,我可以测试“name=”的实际效果,但是即使我去掉整行attr_accessor,也不影响我获取到“name”的参数值。换句话说,attr_getter实际上什么都不做。
但这在理论上是错误的,我该如何纠正这种错误的看法?
class HelloWorld
attr_accessor :name
def initialize(name = "Old name")
@name = name
end
def hello
puts "Hello, I am #{@name}"
end
def intro
puts "I name is #{@name}"
end
end
user = HelloWorld.new()
user.name = "New name"
user.hello #=> Hello, I am New name
user.intro #=> I name is New name
正如评论中提到的那样,它与 Rails 无关,它是 Ruby 核心的一部分。
@name
只是一个实例变量,仅在 HelloWorld
的实例中可用。当您删除 attr_accessor :name
时,您将无法从外部读取或写入 @name
(实际上您可以使用 instance_variable_get
and instance_variable_set
。但您真的需要它吗?)
class HelloWorld
def initialize(name = "Old name")
@name = name
end
end
hello_world = HelloWorld.new
你看不懂
hello_world.name
undefined method `name' for #<HelloWorld:0x00007f3125ea51e8 @name="Old name"> (NoMethodError)
你不会写的
hello_world.name= 'New name'
undefined method `name=' for #<HelloWorld:0x00007f3125ea51e8 @name="Old name"> (NoMethodError)
由您决定是否需要授予对变量的访问权限。
如果您只需要 reader,请使用 attr_reader
. If you want to write it use attr_writer
。如果两者都需要,请保持原样 attr_accessor
.
取决于你。
这在理论上并没有错。实际上,我们可以选择如何运行程序代码。我们在程序代码中使用 OOP 概念。该程序的代码在逻辑上是正确的。
我认为您是在说您的代码是正确的。
class HelloWorld
def setName(name = "Old name")
@name = name
end
def hello
puts "Hello, I am #{@name}"
end
def intro
puts "I name is #{@name}"
end
end
keaton = HelloWorld.new()
keaton.setName("New name")
keaton.hello
keaton.intro
#OUTPUT :
#Hello, I am New name
#I name is New name
您知道 属性 中其他语言的 get 和 set 方法。 get方法returns变量的值和set赋值给name变量
例如:在 C# 中,在 属性
中获取 set 方法
public class HelloWorld
{
private int _name;
public int Age
{
get { return _name; }
set { _name = value; }
}
}
ruby
中的逻辑相同
class HelloWorld
attr_accessor :name
def initialize
@name = name
end
end
我想我明白了,简单地说:
- 原来getter和setter定义实例方法“name and
name=" 分别.
# getter
def name
@name
end
# setter
def name=(value)
@name = value
end
- 即
def name
不是def self.name
,所以不是
class 方法。
attr_accessor
允许 class HelloWorld
及其新实例
使用实例方法 "name and name=".
- 方法“name and name=”的默认值是指定的
初始化的实例变量@name.
def initialize(name = "No name")
@name = name
end
- 方法“hello”和“intro”不能重新赋值(就像setter可以做的),但可以有更丰富的输出结果,比如句子。
我正在 Rails' attr_accessor 上学习 Ruby 的实际功能。在下面的示例中,我知道它将生成“name”和“name=”方法。其中,我可以测试“name=”的实际效果,但是即使我去掉整行attr_accessor,也不影响我获取到“name”的参数值。换句话说,attr_getter实际上什么都不做。
但这在理论上是错误的,我该如何纠正这种错误的看法?
class HelloWorld
attr_accessor :name
def initialize(name = "Old name")
@name = name
end
def hello
puts "Hello, I am #{@name}"
end
def intro
puts "I name is #{@name}"
end
end
user = HelloWorld.new()
user.name = "New name"
user.hello #=> Hello, I am New name
user.intro #=> I name is New name
正如评论中提到的那样,它与 Rails 无关,它是 Ruby 核心的一部分。
@name
只是一个实例变量,仅在 HelloWorld
的实例中可用。当您删除 attr_accessor :name
时,您将无法从外部读取或写入 @name
(实际上您可以使用 instance_variable_get
and instance_variable_set
。但您真的需要它吗?)
class HelloWorld
def initialize(name = "Old name")
@name = name
end
end
hello_world = HelloWorld.new
你看不懂
hello_world.name
undefined method `name' for #<HelloWorld:0x00007f3125ea51e8 @name="Old name"> (NoMethodError)
你不会写的
hello_world.name= 'New name'
undefined method `name=' for #<HelloWorld:0x00007f3125ea51e8 @name="Old name"> (NoMethodError)
由您决定是否需要授予对变量的访问权限。
如果您只需要 reader,请使用 attr_reader
. If you want to write it use attr_writer
。如果两者都需要,请保持原样 attr_accessor
.
取决于你。
这在理论上并没有错。实际上,我们可以选择如何运行程序代码。我们在程序代码中使用 OOP 概念。该程序的代码在逻辑上是正确的。
我认为您是在说您的代码是正确的。
class HelloWorld
def setName(name = "Old name")
@name = name
end
def hello
puts "Hello, I am #{@name}"
end
def intro
puts "I name is #{@name}"
end
end
keaton = HelloWorld.new()
keaton.setName("New name")
keaton.hello
keaton.intro
#OUTPUT :
#Hello, I am New name
#I name is New name
您知道 属性 中其他语言的 get 和 set 方法。 get方法returns变量的值和set赋值给name变量
例如:在 C# 中,在 属性
中获取 set 方法public class HelloWorld
{
private int _name;
public int Age
{
get { return _name; }
set { _name = value; }
}
}
ruby
中的逻辑相同class HelloWorld
attr_accessor :name
def initialize
@name = name
end
end
我想我明白了,简单地说:
- 原来getter和setter定义实例方法“name and name=" 分别.
# getter
def name
@name
end
# setter
def name=(value)
@name = value
end
- 即
def name
不是def self.name
,所以不是 class 方法。 attr_accessor
允许class HelloWorld
及其新实例 使用实例方法 "name and name=".- 方法“name and name=”的默认值是指定的 初始化的实例变量@name.
def initialize(name = "No name")
@name = name
end
- 方法“hello”和“intro”不能重新赋值(就像setter可以做的),但可以有更丰富的输出结果,比如句子。