有人可以向我解释抽象类,接口和mixins之间的区别吗?我之前在我的代码中使用了每个,但我不知道技术差异.
我听说有可能使用扩展方法,但我自己也无法弄明白.如果可能的话,我想看一个具体的例子.
谢谢!
有人会解释我什么时候想要使用Groovy Traits vs. Mixins(@Mixin)与代表(@Delegate)?也许一些权衡和设计问题会有所帮助.
它们似乎都允许重复使用多个"类"行为.谢谢.:-)
这个SO线程也很有帮助:Groovy中@Delegate和@Mixin AST转换之间的区别
快速说明:Scala for Java Refugees第5部分:特征和类型教程中的示例.
假设我有学生,工人,薪水不足和年轻的特征.
我如何声明具有所有这些特征的类(不是实例),CollegeStudent?
注意:我知道简单的案例,例如具有一个或两个特征的CollegeStudent:
class CollegeStudent extends Student with Worker
Run Code Online (Sandbox Code Playgroud) 我想使用Mixin总是为我的子类添加一些init功能,每个类继承自不同的API基类.具体来说,我想创建多个不同的子类,这些子类继承自这些不同的API提供的基类之一和一个Mixin,它将始终以相同的方式执行Mixin初始化代码,而无需代码复制.但是,似乎不会调用Mixin类的__init__函数,除非我在Child类的__init__函数中显式调用它,这不是理想的.我建立了一个简单的测试用例:
class APIBaseClassOne(object):
def __init__(self, *args, **kwargs):
print (" base ")
class SomeMixin(object):
def __init__(self, *args, **kwargs):
print (" mixin before ")
super(SomeMixin, self).__init__(*args, **kwargs)
print (" mixin after ")
class MyClass(APIBaseClassOne):
pass
class MixedClass(MyClass, SomeMixin):
pass
Run Code Online (Sandbox Code Playgroud)
正如您在以下输出中所看到的,Mixin函数的init永远不会被调用:
>>> import test
>>> test.MixedClass()
base
<test.MixedClass object at 0x1004cc850>
Run Code Online (Sandbox Code Playgroud)
有没有办法做到这一点(在调用Mixin时有一个init函数)而不编写每个子类来显式调用Mixin的init函数?(即,不必在每个班级做这样的事:)
class MixedClass(MyClass, SomeMixin):
def __init__(*args, **kwargs):
SomeMixin.__init__(self, *args, **kwargs)
MyClass.__init__(self, *args, **kwargs)
Run Code Online (Sandbox Code Playgroud)
顺便说一句,如果我所有的子类都继承自相同的基类,我意识到我可以创建一个继承自基类和mixin的新中间类,并保持干燥.但是,它们从具有共同功能的不同基类继承.(准确地说是Django Field类).
这似乎是一个菜鸟问题,但简单的答案是在逃避我.我需要调用link_to一个ActionController方法来吐出一个HTML链接. ActionView::Helpers::UrlHelper.link_to调用url_for,但这会调用AV模块的版本而不是控制器的版本.我设法强迫这样做,通过推杆做我想要的
#FIXME there must be a better way to mixin link_to
alias_method :self_url_for, :url_for
include ActionView::Helpers::UrlHelper
alias_method :url_for, :self_url_for
Run Code Online (Sandbox Code Playgroud)
在控制器中.但是,我仍然不确定它为什么会起作用.有人可以解释方法范围并隐藏这里发生的事情吗?什么是更好的混合方式link_to(或者通常只包括模块中的一些方法),所以我可以在控制器中调用它(生成带有链接的flash字符串就是用例.)
请不要讲MVC - 如果有的话,link_to应该在一个单独的模块中url_for.从噪音的数量来看,很多人遇到这个看似微不足道的障碍,并最终浪费了一个小时做"Rails方式",真正想要的是一分钟黑客让我的应用程序现在工作.是否有"Rails方式"可能与助手一起做这件事?还是更好的红宝石方式?
在ruby中,我知道模块功能可以通过使用module_function如此处所示而无需在模块中混合而可用.我可以看到它是如何有用的,因此您可以在模块中使用该功能而无需混合.
module MyModule
def do_something
puts "hello world"
end
module_function :do_something
end
Run Code Online (Sandbox Code Playgroud)
我的问题是,为什么你可能希望这两种方式定义函数.
为什么不呢
def MyModule.do_something
Run Code Online (Sandbox Code Playgroud)
要么
def do_something
Run Code Online (Sandbox Code Playgroud)
在哪种情况下,将函数混合使用或用作静态方法是有用的?
我正在尝试使用Ruby模块(mixins).
我有test.rb:
#!/usr/bin/env ruby
require_relative 'lib/mymodule'
class MyApp
include MyModule
self.hallo
end
Run Code Online (Sandbox Code Playgroud)
和lib/mymodule.rb:
module MyModule
def hallo
puts "hallo"
end
end
Run Code Online (Sandbox Code Playgroud)
非常简单的设置.但它不起作用:(:
ruby test.rb
test.rb:8:in `<class:MyApp>': undefined method `hallo' for MyApp:Class (NoMethodError)
from test.rb:6:in `<main>'
Run Code Online (Sandbox Code Playgroud)
我的错误在哪里?
我想要实现的是正确实施
def dynamix[A, B](a: A): A with B
Run Code Online (Sandbox Code Playgroud)
我可能知道B是什么,但不知道A是什么(但如果B有自我类型,那么我可以在A上添加一些约束).scala编译器对上面的签名很满意,但我还不知道实现的样子 - 如果可能的话.
我想到了一些选择:
你有其他可能有用的想法吗?你会推荐哪种方式?期待什么样的"挑战"?
或者我应该忘记它,因为目前的Scala限制是不可能的?
我的问题背后的意图:说我有一个业务工作流程,但它不是太严格.一些步骤具有固定顺序,但其他步骤没有,但最后必须完成所有步骤(或者其中一些步骤需要进一步处理).
更具体的例子:我有一个A,我可以添加B和C. 我不在乎先做哪个,但最后我需要A带B和C.
评论:我对Groovy不太了解,但是我想出了这个问题,我想这或多或少与我想要的一样,至少在构思上.