我是Ruby的新手,所以让我先描述一下我的问题的背景: 我有一个json作为输入,它具有以下键/值对:
{
"service": "update"
}
该值有许多不同的值,例如:insert,delete等。 接下来有一个方法x来处理不同的请求:
def x(input)
case input[:service]
services = GenericService.new
when "update"
result = services.service(UpdateService.new,input)
when "insert"
result = services.service(InsertService.new,input)
when "delete"
result = services.service(DeleteService.new,input)
....
....
else
raise "Unknown service"
end
puts JSON.pretty_generate(result)
end
困扰我的是我仍然需要使用switch语句来检查String值(让我想起'ugh的实例......)。有更清洁的方式(不需要使用开关)?
最后,我尝试搜索我的问题的答案,但没有成功,如果我错过了,请随时评论相关问题。
更新:我想将字符串转换为相关的类名,如下所示:How do I create a class instance from a string name in ruby?然后调用result = services.services(x.constantize.new,input) ,然后课程的类名需要匹配json的输入。
答案 0 :(得分:3)
您可以尝试以下内容:
def x(input)
service_class_name = "#{input[:service].capitalize}Service"
service_class = Kernel.const_get(service_class_name)
service_class.new(input).process
end
此外,您可能想要检查这是否是一个有效的服务类名称。
我不明白为什么要将服务传递给GenericService
这看起来很奇怪。让服务做它的工作。
答案 1 :(得分:1)
如果你试图通过它的名称来实现一个类,你实际上是在谈论反思而不是多态。
在Ruby中,你可以通过这种方式实现这一目标:
byName = Object.const_get('YourClassName')
或者如果你在Rails应用程序中
byName= 'YourClassName'.constantize
希望这有帮助
答案 2 :(得分:0)
只是初步想法,但你可以这样做:
eval(services.service("#{input[:service].capitalize}Service.new, #{input})") if valid_service? input[:service]
def valid_service?
w%(delete update insert).include? input[:service]
end
人们无疑会大喊大叫,需要大量使用eval