我经常发现自己想要编写以下形式的通用类定义
public class Foo<ActualType extends Foo<ActualType>>
例如在这样的设置中:
public interface ChangeHandler<SourceType> {
public void onChange(SourceType source);
}
public class Foo<ActualType extends Foo<ActualType>> {
private final List<ChangeHandler<ActualType>> handlers = new ArrayList<>();
public void addChangeHandler(ChangeHandler<ActualType> handler) {
handlers.add(handler);
}
@SuppressWarnings("unchecked")
protected void reportChange() {
for (ChangeHandler<ActualType> handler: handlers)
handler.onChange((ActualType) this);
}
}
public class Bar extends Foo<Bar> {
// things happen in here that call super.reportChange();
}
public static void main(String[] args) throws IOException {
Bar bar = new Bar();
bar.addChangeHandler(new ChangeHandler<Bar>() {
@Override
public void onChange(Bar source) {
// Do something with the changed object
}
});
}
这里的 change-event 只是一个例子。这是一个更普遍的问题,每当我想允许父类(super class)为每个特定的子类提供“个性化”的功能时(不确定如何更好地表达这个......在示例中“个性化”之上的事实是 ChangeHandler 是用实际子类型 (Bar) 的对象调用的,而不是用父类(super class)的类型 (Foo) 调用处理程序)。
不知何故,这种方法对我来说似乎有点困惑。它实际上允许潜在的问题,因为没有什么能阻止我定义:
public class Baz extends Foo<Bar> { /* ... */ }
有没有更清洁的替代品?
chalice 是一些总是被定义为包含当前类的类型参数,比如 this.getClass() 的静态版本,它允许我写这样的东西:
public class Foo {
private final List<ChangeHandler<this.Class>> handlers = new ArrayList<>();
public void addChangeHandler(ChangeHandler<this.Class> handler) {
handlers.add(handler);
}
protected void reportChange() {
for (ChangeHandler<this.Class> handler: handlers)
handler.onChange(this);
}
}
对于 Bar 类型的类,this.Class 等于 Bar。
最佳答案
这是一个非常抽象的问题。在我看来,对“如何使它更清洁”的简短回答是:只在需要的地方使用泛型。
public class List<T extends List<T>>
这是想表达什么(替代)?一个只允许持有(T 扩展)其他列表的列表,这些列表本身持有 Ts(列表),正如我们之前知道的那样,这些列表只允许持有......等等。有点像通告,我不明白你怎么会得到这样的结果?
public interface ChangeHandler<SourceType> {
public void onChange(SourceType source);
}
为什么要在这里使用泛型?如果您想要一个可以处理多种资源类型的更改处理程序,那么您可以创建一个所有实际源都继承自的父类(super class),或者创建一个由源实现的接口(interface)。这样您就可以准确指定源公开的内容。或者,源可以在通知时创建一个源对象,而不是传递“this”(那么它更像是一条消息)。例如:
public interface ChangeHandler {
public void onChange(Source source);
}
public abstract class Source {
private List<ChangeHandler> handlers;
protected int nr;
public Source(int nr) {
this.nr = nr;
}
public abstract Something getSomething();
public String toString() {
return "SRC" + nr;
}
...
private notify(int index) {
handlers.get(i).onChange(this);
}
}
public class Foo extends Source {
public Foo(int nr) {
super(nr);
}
public String toString() {
return super.toString() + "Foo";
}
public Something getSomething() {
return new Something();
}
}
你永远不需要施法……是吗?我不确定我是否理解这个问题。
关于java - 避免形式为 For<Actual Type extends Foo<Actual Type>> 的泛型类型,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30382847/
我有一个对象has_many应呈现为xml的子对象。这不是问题。我的问题是我创建了一个Hash包含此数据,就像解析器需要它一样。但是rails自动将整个文件包含在.........我需要摆脱type="array"和我该如何处理?我没有在文档中找到任何内容。 最佳答案 我遇到了同样的问题;这是我的XML:我在用这个:entries.to_xml将散列数据转换为XML,但这会将条目的数据包装到中所以我修改了:entries.to_xml(root:"Contacts")但这仍然将转换后的XML包装在“联系人”中,将我的XML代码修改为
我想向我的Controller传递一个参数,它是一个简单的复选框,但我不知道如何在模型的form_for中引入它,这是我的观点:{:id=>'go_finance'}do|f|%>Transferirde:para:Entrada:"input",:placeholder=>"Quantofoiganho?"%>Saída:"output",:placeholder=>"Quantofoigasto?"%>Nota:我想做一个额外的复选框,但我该怎么做,模型中没有一个对象,而是一个要检查的对象,以便在Controller中创建一个ifelse,如果没有检查,请帮助我,非常感谢,谢谢
我真的很习惯使用Ruby编写以下代码:my_hash={}my_hash['test']=1Java中对应的数据结构是什么? 最佳答案 HashMapmap=newHashMap();map.put("test",1);我假设? 关于java-等价于Java中的RubyHash,我们在StackOverflow上找到一个类似的问题: https://stackoverflow.com/questions/22737685/
关闭。这个问题需要detailsorclarity.它目前不接受答案。想改进这个问题吗?通过editingthispost添加细节并澄清问题.关闭8年前。Improvethisquestion在首页我有:汽车:VolvoSaabMercedesAudistatic_pages_spec.rb中的测试代码:it"shouldhavetherightselect"dovisithome_pathit{shouldhave_select('cars',:options=>['volvo','saab','mercedes','audi'])}end响应是rspec./spec/request
似乎无法为此找到有效的答案。我正在阅读Rails教程的第10章第10.1.2节,但似乎无法使邮件程序预览正常工作。我发现处理错误的所有答案都与教程的不同部分相关,我假设我犯的错误正盯着我的脸。我已经完成并将教程中的代码复制/粘贴到相关文件中,但到目前为止,我还看不出我输入的内容与教程中的内容有什么区别。到目前为止,建议是在函数定义中添加或删除参数user,但这并没有解决问题。触发错误的url是http://localhost:3000/rails/mailers/user_mailer/account_activation.http://localhost:3000/rails/mai
我正在处理旧代码的一部分。beforedoallow_any_instance_of(SportRateManager).toreceive(:create).and_return(true)endRubocop错误如下:Avoidstubbingusing'allow_any_instance_of'我读到了RuboCop::RSpec:AnyInstance我试着像下面那样改变它。由此beforedoallow_any_instance_of(SportRateManager).toreceive(:create).and_return(true)end对此:let(:sport_
我使用Nokogiri(Rubygem)css搜索寻找某些在我的html里面。看起来Nokogiri的css搜索不喜欢正则表达式。我想切换到Nokogiri的xpath搜索,因为这似乎支持搜索字符串中的正则表达式。如何在xpath搜索中实现下面提到的(伪)css搜索?require'rubygems'require'nokogiri'value=Nokogiri::HTML.parse(ABBlaCD3"HTML_END#my_blockisgivenmy_bl="1"#my_eqcorrespondstothisregexmy_eq="\/[0-9]+\/"#FIXMEThefoll
当我在我的Rails应用程序根目录中运行rakedoc:app时,API文档是使用/doc/README_FOR_APP作为主页生成的。我想向该文件添加.rdoc扩展名,以便它在GitHub上正确呈现。更好的是,我想将它移动到应用程序根目录(/README.rdoc)。有没有办法通过修改包含的rake/rdoctask任务在我的Rakefile中执行此操作?是否有某个地方可以查找可以修改的主页文件的名称?还是我必须编写一个新的Rake任务?额外的问题:Rails应用程序的两个单独文件/README和/doc/README_FOR_APP背后的逻辑是什么?为什么不只有一个?
我正在尝试使用boilerpipe来自JRuby。我看过guide从JRuby调用Java,并成功地将它与另一个Java包一起使用,但无法弄清楚为什么同样的东西不能用于boilerpipe。我正在尝试基本上从JRuby中执行与此Java等效的操作:URLurl=newURL("http://www.example.com/some-location/index.html");Stringtext=ArticleExtractor.INSTANCE.getText(url);在JRuby中试过这个:require'java'url=java.net.URL.new("http://www
我有一个名为posts的模型,它有很多附件。附件模型使用回形针。我制作了一个用于创建附件的独立模型,效果很好,这是此处说明的View(https://github.com/thoughtbot/paperclip):@attachment,:html=>{:multipart=>true}do|form|%>posts中的嵌套表单如下所示:prohibitedthispostfrombeingsaved:@attachment,:html=>{:multipart=>true}do|at_form|%>附件记录已创建,但它是空的。文件未上传。同时,帖子已成功创建...有什么想法吗?