2007-06-28
self.与@的区别——别被原有的思维方式误导
关键字: ruby rails ActiveRecord
最近在学习Rails时把先前在Java中的一些习惯性思维带了过了,结果在遇到self.与@时被这种思维方式给误导了。
遇到这个问题是在使用AcriveRecord时,在修改或者新增记录时需要添加时间戳。首先使用self.posted_at=Time.now来修改字段,一切正常。后来想到在哪篇文章中好像说过self.与Java中的this差不多,这样就不自觉的把posted_at当作了实例变量处理,试了一下用@posted_at=Time.now,没有出错,但是记录的时间并没有被更新。
起初想到书上说ActiveRecord在第一次访问那个类时,将根据表结构信息,自动添加列到实例变量并增加对这些变量的访问器。似乎没有错呀,既然是实例变量不就是@吗?
用instance_values查看才恍然大悟,@attributes这个实例变量保存了各个字段的值。ActiveRecord在初始化这一个类时,添加的实例变量并不是一个数据库字段对应于一个实例变量,而是放到了@atributes里。然后添加了对各个字段的访问器。通过methods方法可以查看实例中的所有方法,可以看到有posted和posted=这两个访问器方法。
self.!=this
self.是方法调用,而不是直接访问实例变量。
从这个错误中,我也清楚了下面三种写法的区别:
1. self.id= 调用id方法。
2. @id= 直接访问实例变量
3. id= 如果前面不加self.,解释器将认为你要给一个局部变量赋值,而不会认为你是要调用id=这个方法修字段id的数据。
遇到这个问题是在使用AcriveRecord时,在修改或者新增记录时需要添加时间戳。首先使用self.posted_at=Time.now来修改字段,一切正常。后来想到在哪篇文章中好像说过self.与Java中的this差不多,这样就不自觉的把posted_at当作了实例变量处理,试了一下用@posted_at=Time.now,没有出错,但是记录的时间并没有被更新。
起初想到书上说ActiveRecord在第一次访问那个类时,将根据表结构信息,自动添加列到实例变量并增加对这些变量的访问器。似乎没有错呀,既然是实例变量不就是@吗?
用instance_values查看才恍然大悟,@attributes这个实例变量保存了各个字段的值。ActiveRecord在初始化这一个类时,添加的实例变量并不是一个数据库字段对应于一个实例变量,而是放到了@atributes里。然后添加了对各个字段的访问器。通过methods方法可以查看实例中的所有方法,可以看到有posted和posted=这两个访问器方法。
self.!=this
self.是方法调用,而不是直接访问实例变量。
从这个错误中,我也清楚了下面三种写法的区别:
1. self.id= 调用id方法。
2. @id= 直接访问实例变量
3. id= 如果前面不加self.,解释器将认为你要给一个局部变量赋值,而不会认为你是要调用id=这个方法修字段id的数据。
- 14:03
- 浏览 (2153)
- 评论 (9)
- 分类: Ruby&Rails
- 进入论坛
- 相关推荐
评论
hideto
2007-06-30
在set_name里面调用name=,不会调用obj.name=,而是把name当作local变量,我理解你的意思了gigix,笨啊
hideto
2007-06-30
set_name方法对name作修改,而不是对@name做修改,当然结果是@name不变
所以说,不同语言不同语法而已
所以说,不同语言不同语法而已
gigix
2007-06-30
hideto 写道
gigix 写道
呵呵,另一个有趣的是
调用set_name不会对@name设值,因为Ruby认为set_name里的name是一个局部变量……
@name = "" attr_writer :name def set_name(input_name) name = input_name end
调用set_name不会对@name设值,因为Ruby认为set_name里的name是一个局部变量……
name和@name本来就不一样
attr_writer :name
这句会创建name=方法的
hideto
2007-06-30
Jamsa 写道:
最近在学习Rails时把先前在Java中的一些习惯性思维带了过了,结果在遇到self.与@时被这种思维方式给误导了。
遇到这个问题是在使用AcriveRecord时,在修改或者新增记录时需要添加时间戳。首先使用self.posted_at=Time.now来修改字段,一切正常。后来想到在哪篇文章中好像说过self.与Java中的this差不多,这样就不自觉的把posted_at当作了实例变量处理,试了一下用@posted_at=Time.now,没有出错,但是记录的时间并没有被更新。
起初想到书上说ActiveRecord在第一次访问那个类时,将根据表结构信息,自动添加列到实例变量并增加对这些变量的访问器。似乎没有错呀,既然是实例变量不就是@吗?
用instance_values查看才恍然大悟,@attributes这个实例变量保存了各个字段的值。ActiveRecord在初始化这一个类时,添加的实例变量并不是一个数据库字段对应于一个实例变量,而是放到了@atributes里。然后添加了对各个字段的访问器。通过methods方法可以查看实例中的所有方法,可以看到有posted和posted=这两个访问器方法。
self.!=this
self.是方法调用,而不是直接访问实例变量。
从这个错误中,我也清楚了下面三种写法的区别:
1. self.id= 调用id方法。
2. @id= 直接访问实例变量
3. id= 如果前面不加self.,解释器将认为你要给一个局部变量赋值,而不会认为你是要调用id=这个方法修字段id的数据。
遇到这个问题是在使用AcriveRecord时,在修改或者新增记录时需要添加时间戳。首先使用self.posted_at=Time.now来修改字段,一切正常。后来想到在哪篇文章中好像说过self.与Java中的this差不多,这样就不自觉的把posted_at当作了实例变量处理,试了一下用@posted_at=Time.now,没有出错,但是记录的时间并没有被更新。
起初想到书上说ActiveRecord在第一次访问那个类时,将根据表结构信息,自动添加列到实例变量并增加对这些变量的访问器。似乎没有错呀,既然是实例变量不就是@吗?
用instance_values查看才恍然大悟,@attributes这个实例变量保存了各个字段的值。ActiveRecord在初始化这一个类时,添加的实例变量并不是一个数据库字段对应于一个实例变量,而是放到了@atributes里。然后添加了对各个字段的访问器。通过methods方法可以查看实例中的所有方法,可以看到有posted和posted=这两个访问器方法。
self.!=this
self.是方法调用,而不是直接访问实例变量。
从这个错误中,我也清楚了下面三种写法的区别:
1. self.id= 调用id方法。
2. @id= 直接访问实例变量
3. id= 如果前面不加self.,解释器将认为你要给一个局部变量赋值,而不会认为你是要调用id=这个方法修字段id的数据。
只是不同语言的语法不一样罢了,和思维方式没什么关系
hideto
2007-06-30
gigix 写道
呵呵,另一个有趣的是
调用set_name不会对@name设值,因为Ruby认为set_name里的name是一个局部变量……
@name = "" attr_writer :name def set_name(input_name) name = input_name end
调用set_name不会对@name设值,因为Ruby认为set_name里的name是一个局部变量……
name和@name本来就不一样
笨笨狗
2007-06-28
这些问题,R4R里面就有讲的,此书虽然罗嗦,但是还不错
logo
2007-06-28
楼主对self的理解不准确。self在不同的作用域具有不同的含义,《ruby for rails》专门有一章内容就是讲self的。
具体在一个类的一个方法内部使用self,那么这个self代表该类的当前对象实例,因此:self.id= 就是调用当前该类对象实例的id=()方法。此时一定要加self,否则ruby解析器优先把id解析为一个方法内部的局部变量。
具体在一个类的一个方法内部使用self,那么这个self代表该类的当前对象实例,因此:self.id= 就是调用当前该类对象实例的id=()方法。此时一定要加self,否则ruby解析器优先把id解析为一个方法内部的局部变量。
gigix
2007-06-28
呵呵,另一个有趣的是
调用set_name不会对@name设值,因为Ruby认为set_name里的name是一个局部变量……
@name = "" attr_writer :name def set_name(input_name) name = input_name end
调用set_name不会对@name设值,因为Ruby认为set_name里的name是一个局部变量……
rainchen
2007-06-28
"在修改或者新增记录时需要添加时间戳"
针对这个问题,
你只需增加两个字段created_at和updated_at,类型为:datetime
无需其他设置,就能自动达到你的要求了
至于如何转化为精确的时间戳,请其他达人解答
更多魔术字段见:
http://wiki.rubyonrails.com/rails/pages/MagicFieldNames
针对这个问题,
你只需增加两个字段created_at和updated_at,类型为:datetime
无需其他设置,就能自动达到你的要求了
至于如何转化为精确的时间戳,请其他达人解答
更多魔术字段见:
http://wiki.rubyonrails.com/rails/pages/MagicFieldNames
- 浏览: 46336 次

- 详细资料
搜索本博客
最近加入圈子
最新评论
-
重新整理后的Oracle OAF学 ...
太好了!谢死你了!
-- by chenpu -
ExtJS中FormPanel实现数 ...
请教一下楼主,本地json数据如何实现分页?单击下一页时,怎样在js中得到当前的 ...
-- by gaipai -
重新整理后的Oracle OAF学 ...
这个格式的高亮显示都看不清了
-- by qinglangee -
ExtJS中FormPanel实现数 ...
把你的后台代码发出来看看啊 光说返回JSON的格式,看看你到底是怎么返回的啊 y ...
-- by yongtree -
重新整理后的Oracle OAF学 ...
best regards
-- by luoluo_guo






评论排行榜