自定义.is_a?在Ruby中
问题描述:
是否可以在Ruby中创建自定义is_a?
?自定义.is_a?在Ruby中
我有一个字符串,可以是我需要检查和决定的UID或昵称。
UID:001ABC123
(始于3数字和6个字母结尾)
昵称:john
(可以是任何东西,但从来没有以数字开头)
我希望能够做到:
t = '001ABC123'
if t.is_a? UID
...
end
这可能吗?
答
有关红宝石的伟大之处之一是您可以重新开放任何课程。所以这样的一个实现可能是这样的:
class String
def is_a?(type)
return true if type == UID
end
end
+0
该解决方案返回'nil'作为''string'.is_a?(String)',它应该是'true',并且很可能会在第三方库中破坏某些东西 – Vasfed
答
不污染全球String
- 利用改进:
class UID < String
end
module CustomStringIsA
refine String do
def is_a? what
if what == UID
self == '123'
else
super
end
end
end
end
puts '123'.is_a?(UID) # false
using CustomStringIsA
puts '123'.is_a?(Fixnum) # false
puts '123'.is_a?(UID) # true
但更好的使用===
,这样你就可以使用case
这样的:
class UID < String
def self.=== str
str === '123'
end
end
class UID2 < String
def self.=== str
str === '456'
end
end
case '456'
when UID
puts 'uid'
when UID2
puts 'uid2'
else
puts 'else'
end
答
如果您正在寻找简洁的检查方式,为什么不使用正则表达式并使用=~
运算符进行匹配。
这与使用自定义is_a?
一样整洁,不需要搞乱String
类。
例如:
UID = /^[[:digit:]]{3}[[:alnum:]]{6}$/
t = '001ABC123'
if t =~ UID
#...
end
添加'is_a'全球的字符串是一个非常糟糕的主意。如果项目中的任何其他人决定也将“is_a”方法添加到字符串 - 你会得到一些有趣的错误。 –