- iOS/Objective-C 元类和类别
- objective-c - -1001 错误,当 NSURLSession 通过 httpproxy 和/etc/hosts
- java - 使用网络类获取 url 地址
- ios - 推送通知中不播放声音
为什么我不能这样做/是否有解决方法来实现此目的:
package myPackage;
public class A {
public class B {
}
}
package myPackage;
import myPackage.A.B;
public class C extends B {
}
package myPackage;
public class Main {
public static void main(String[] args) {
A myA = new A();
C myC = myA.new C();
}
}
两个编译错误是
在 public class C extends B
上,由于某些中间构造函数调用,类型 A 的封闭实例不可用
在 C myC = myA.new C();
上,A.C 无法解析为类型
坦率地说,我认为概念上的想法是合理的:我想创建 B 的子类,这样当我为 A 创建 B 时,我可以选择使其具有 B 中的功能或 C 中的功能。
我不想要的四种解决方法/解决方案,以及我不想要它们的原因:
“解决方案:将 C 放在 A 中。”我不想要这个,因为如果我不能修改 A.java 的代码怎么办(有些应用程序有这个限制)?如果 A 是另一个 API 的一部分怎么办?然后我必须为 C 创建一个新文件,就像我在此处所做的那样。
“解决方案:将 C 放在扩展 A 的类 D 中。”我不想要这个,因为 C 被限制为只能在 D 类型的实例上实例化。我想创建一个扩展 B 的类,它可以在 A 类型的所有实例上实例化(有需要这个的应用程序)。因此,我需要 C 不包含在另一个类中,就像我在此处所做的那样。
(作为问题编辑添加 - 请参阅 JoshuaTaylor 对代码示例的回答)“解决方案:使 B 静态化。”我不想要这个,因为如果 B 中的功能需要访问其封闭的 A 实例怎么办(有些应用程序需要这个)?因此,我需要 B 不是静态的,就像我在这里所做的那样。 (第二个问题编辑:您可以使 B 静态并让它的构造函数接受它的封闭实例,将它保存在一个 protected 变量中以供其子级访问,但这不如 RealSkeptic 接受的答案优雅)
<已删除。请参阅底部的编辑。
因此,如果您的回答建议我执行上述操作之一,那么它不是这个问题的答案,即使它可能对其他人有用。
如果您的回答是“这只是 Java 语言的一个缺陷,您根本不能完成那个概念性想法”,这是一个不错的答案,您应该发布它。不过只是一个警告:如果你错了,我会推迟将你的答案标记为已接受。如果这是你的答案,如果你能解释为什么对语言有这种限制(因为这是这个问题的标题),我将不胜感激。
感谢您提供的所有帮助。
编辑:JoshuaTaylor 的回答提出了一个有效选项:您可以扩展 B anonymously并避免像 RealSkeptic 接受的答案那样编写构造函数。我最初放弃了这个想法,因为它不允许您通过“A.this”访问 C 的 A 封闭实例。但是,从那以后我了解到 C 没有 A 的封闭实例,除非它在 A 的定义中明确定义为嵌套类。所以请注意:下面的任何解决方案都不允许您通过在 C 的方法中写入“A.this”来访问包含 B 的 C 祖先的 A 的封闭实例。类只能使用“.this”来访问它们的类型专门嵌套在。但是,如果 B 具有访问 A 的封闭实例的功能,则需要通过 JoshuaTaylor 方法的匿名类或通过 RealSkeptic 方法的任何其他类。
最佳答案
嗯,这可以做到,但你必须记住,每个构造函数都需要显式或隐式地调用其 super 构造函数。这就是为什么您会收到 “由于某些中间构造函数调用,类型 A 的封闭实例不可用” 错误的原因。 C
的无参数构造函数试图隐式调用 B
的无参数构造函数,如果没有 A
.
因此,您将 C
修改为:
public class C extends B {
public C(A enclosing) {
enclosing.super();
}
}
然后您可以使用以下方法创建一个新的C
:
A myA = new A();
C myC = new C(myA);
评论中问题的答案
@Andi Turner 问:
If you are explicitly passing in an A to the constructor of C, can't C now be static, and have A as a "plain old" member variable in C on which you invoke the required methods?
需要注意的是C既不是static也不是内部类。它是一个扩展内部类 B 的独立公共(public)类。C 的作者可能不知道类 B 的实现,因此它不知道将使用 A 的哪些方法,也无法访问任何私有(private)成员A 的,因为 C 不是 A 的成员。但是 B 是,并且 B 需要 A 实例。另一种方法是组合而不是继承(其中 C 持有一个 B 实例并将操作委托(delegate)给它),但是如果它想创建 B 实例而不是将其传递到内部,它仍然需要一个 A 实例,尽管它会使用 enclosing.new B
而不是 enclosing.super
。
@rajuGT 问:
Is C is an individual entity? if so, why does it need A object? and what is the association between myA and myC in this case?
是的,C 是一个单独的实体。它自己的任何方法都不需要 A。但是,如果它试图从 B 调用(或继承但不覆盖)涉及访问 A 的方法 - 那么 B 的实现需要 A。当然,形式上,B 的任何实例甚至都需要引用 A如果它实际上没有使用它。 myA
和 myC
之间的关联是 myA
是 myC
的直接封闭实例到 B
。该术语取自 section 8.1.3 of the JLS :
For every superclass
S
ofC
which is itself a direct inner class of a class or interfaceSO
, there is an instance ofSO
associated withi
, known as the immediately enclosing instance ofi
with respect toS
. The immediately enclosing instance of an object with respect to its class' direct superclass, if any, is determined when the superclass constructor is invoked via an explicit constructor invocation statement (§8.8.7.1)
此用法的官方引用
这种用法被称为限定父类(super class)构造函数调用语句,并在JLS, section 8.8.7.1 - Explicit Constructor Invocations 中提到。 .
Superclass constructor invocations begin with either the keyword
super
(possibly prefaced with explicit type arguments) or a Primary expression or an ExpressionName. They are used to invoke a constructor of the direct superclass. They are further divided:
Unqualified superclass constructor invocations begin with the keyword
super
(possibly prefaced with explicit type arguments).Qualified superclass constructor invocations begin with a Primary expression or an ExpressionName. They allow a subclass constructor to explicitly specify the newly created object's immediately enclosing instance with respect to the direct superclass (§8.1.3). This may be necessary when the superclass is an inner class.
在该部分的末尾,您可以找到显式构造函数调用语句的示例,包括这种用法。
关于java - 为什么外部类不能扩展内部类?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/33026474/
我试图弄清楚如何为聊天气泡制作外 Angular 圆形设计,以获得所需的结果: 我必须使用气泡作为不同背景的组件,没有相同和纯色,但有一些设计元素,所以气泡周围的空间必须是透明的: 我试过将元素添加为
我尝试了 display:table-cell 但它没有用。我怎样才能在div中显示这个词。现在它显示溢出了 div。我在我的网页上使用 CSS2。提前致谢。 Visit W3Schools
我有一个使用 CSS 隐藏在 View (对于移动设备)之外的菜单: #filter-column { position:absolute; left:-400px; } 当用户单击链
我想创建一个这样的问题行 http://imageshack.us/photo/my-images/200/questionh.png/ 此时我的html源是: question label
我要mock a class with Ruby . 如何编写处理样板代码的方法? 以下代码: module Mailgun end module Acani def self.mock_mail
请不要担心循环,但我的问题是关于这些关键字:outer、middle 和 inner。它们不是声明为实例变量,为什么IDE让代码编译?我在谷歌上搜索了一下,这是java标签吗? Java中的某种关键字
我有一个数据框(df),看起来像, Id Name Activity. 1 ABC a;sldkj kkkdk 2 two
Elasticsearch内存中有哪些东西可以使搜索如此快速? 是所有json本身都在内存中,还是仅倒排索引和映射将在内存中24 * 7? 最佳答案 这是一个很好的问题,然后简而言之就是: 不仅仅是数
我正在尝试添加用户在用户界面上选择的值。对于数据库中的特定列,我已经与数据库建立了连接,当我按“保存”时,新的 id 会添加到数据库中,控制台中不会显示任何错误,但我要提交的值不会放入数据库,我怎样才
我不确定这个问题是否应该涉及电子领域,但由于它是关于编程的,所以我在这里问了它。 我正在制作一个数字时钟,使用由移位寄存器供电的 LED,而不是 7 段显示器。无论如何,当使用 CCS 编译代码时,我
我希望用户在 div 中选择文本 (html)。然而,这样做会在浏览器中显示选择背景,也在 div 之外。 我可以用(参见 http://jsfiddle.net/lborgman/aWbgT/)来防
我有以下 Razor View @{ ViewBag.Title = "UserCost"; }
我使用 KineticJS 和 D3.js 制作了以下内容。当用户将鼠标悬停在其中一个点上时,我使用 KineticJS 让我弹出工具提示。但是,由于 Canvas 的边界,工具提示似乎被切断了。有没
关闭。这个问题需要更多focused .它目前不接受答案。 想改进这个问题吗? 更新问题,使其只关注一个问题 editing this post . 关闭 2 年前。 Improve this qu
我正在使用 primefaces 学习 Java Web 和 jsf。 我的项目当前只有一个index.xhtml 文件,当我访问localhost:8080/appname/时,index.xhtm
我是 ios 新手。 我有一个 View ,其中我使用 Quarts 核心绘制了一个圆圈。 我在该圆圈中放置了一个 UIButton,并赋予了拖放该按钮的功能。 现在我想要限制按钮不能被拖出那个圆圈区
这个问题已经有答案了: How to add two strings as if they were numbers? [duplicate] (20 个回答) How to force JS to
我正在创建简单的文本从右侧滑动到页面的 css 动画。我正在使用 jQuery 通过向元素添加一个类来触发动画。但是起始位置必须在视口(viewport)之外,这会触发底部滚动条出现。如何预防? 这是
我编写了一个简单的代码来评估一段代码并将输出写入文件。这样它减少了我的一些,因为我需要很多很多文件,每一行都包含返回值! 无论如何,我正在使用的代码是: #!/usr/bin/ruby -w def
所以我试图在我的一款游戏中加入一个非常基本的“手电筒”式的东西。 我让它工作的方式是在我的游戏屏幕顶部有一个层,这个层会绘制一个黑色矩形,不透明度约为 80%,在我的游戏场景顶部创建黑暗的外观。 cc
我是一名优秀的程序员,十分优秀!