【问题标题】:How to use inner class in practical [closed]如何在实际中使用内部类[关闭]
【发布时间】:2013-08-14 17:12:37
【问题描述】:

为什么有人会使用inner class?使用local classsubclass 可以实现相同的功能。

也可以举个例子。

【问题讨论】:

标签: java inner-classes anonymous-inner-class


【解决方案1】:

内部类可用于许多功能性案例。它们具有两个优点:

  1. 内部类可以看到外部类的字段(如果它不是静态的)。这意味着您不必处理外部类字段,就好像它们来自外部类一样。这意味着您的内部类需要外部类的实例才能工作。 如果你的类是静态的,那么它就像一个独立的类。
  2. 内部类与其所属类紧密相关。因此,即使它是静态的,您也可以通过其名称知道它与其所属的类相关。

话虽如此,您可以理解内部类必须用于事物所属的地方。

所以最可能的情况是当您不需要外部类之外的内部类时。例如:

class ScreenCapture {
  class CaptureButtonListener implements ClickListener {
     public void onClick( ClickEvent click ) {
       //..capture
       pressCount++;
     }
  }

  Button button = new Button("capture");
  int pressCount = 0;

  void addListeners() {
    button.addClickListener( new CaptureButtonListener() );
  }
}

如你所见:

  • 您将永远不需要 ScreenCapture 之外的 CaptureButtonListener。所以最好隐藏它(甚至将其声明为私有或受保护)。
  • 内部类正在访问一个不属于它的字段:pressCount。这是可能的,因为它的实例与 ScreenCapture 实例相关联:您不能在静态方法中创建 new CaptureButtonListener():您必须在实例方法中使用它。

另一方面,静态内部类仅用于组织目的(也就是说两个类是相关的)。我将使用静态内部类修改前面的示例:

public class ScreenCapture {
  public static class CaptureButtonListener implements ClickListener {
    protected ScreenCapture controller;
    public CaptureButtonListener( ScreenCapture controller ) {
      this.controller = controller;
    }

     public void onClick( ClickEvent click ) {
       //..capture
       controller.pressCount++;
     }
  }

  Button button = new Button("capture");
  int pressCount = 0;

  public void captureRequested() {
    //do capture...
    pressCount++;
  }

  void addListeners() {
    button.addClickListener( new CaptureButtonListener(this) );
  }
}

请注意,在这种情况下:

  • 变量 pressCount 不再可以从内部类访问:您必须指定它所属的实例。
  • 您可以从外部实例化 CaptureButtonListener,但您可以直接从其名称中看到:new ScreenCapture.CaptureButtonListener( screenCaptureInstance ) 它与 ScreenCapture 类相关(提高了代码的可读性)

现在您可能想知道为什么要创建一个无法访问其所有者字段的内部类?你是对的:在我们的例子中这不是很明智,因为你必须将 ScreenCapture 的一个实例传递给构造函数(所以你不能将它与 ScreenCapture 以外的任何其他类一起使用)。这只是为了证明差异。

以下示例将充分说明前一个示例:

你可以在 ScreenCapture 中将你的监听器声明为一个公共静态接口

class ScreenCapture {
  public static interface class CaptureRequestListener {
     public void captureRequested( ClickEvent click );
  }
}

这样你可以传递“如何处理捕获请求”的 ScreenCapture 实现

同样,接口的实现会知道他们正在实现特定于 ScreenCapture 的东西,因为它们会实现

public class MyImpl implements ScreenCapture.CaptureRequestListener {
  public void captureRequested( ClickEvent click ) {
    // I will count requests instead
  }
}

因此,您的代码比将其放在每个文件组织的单独类中更清晰。

您还可以拥有一个基本处理类(作为内部类的常见任务的抽象实现)

我希望一切都清楚:-) 最好的祝福, 齐德

【讨论】:

    【解决方案2】:

    内部类的作用域是声明它们的类,因此根据您的作用域,您将决定创建一个内部类。是的,如果您的范围是方法的本地,您可以创建本地类,因此做出决定是由范围驱动的。

    我建议阅读以下内容以获得更多了解和知识URL

    【讨论】:

      【解决方案3】:

      内部类可以实现多重继承。所以如果你的类已经扩展了一个类,你可以通过内部类扩展更多的类。

      您还应该检查集合 API 以了解其使用情况。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2013-08-15
        • 2011-11-05
        • 1970-01-01
        • 2012-09-19
        • 2018-12-01
        • 1970-01-01
        • 2020-06-15
        • 2011-02-17
        相关资源
        最近更新 更多