Использование внутреннего класса - PullRequest
22 голосов
/ 29 октября 2010

Я могу понять, что такое внутренний класс и как писать программы.Мой вопрос: в какой ситуации программистам действительно нужен внутренний класс?

Ответы [ 6 ]

30 голосов
/ 29 октября 2010

Иногда есть некоторая функциональность, которая лучше всего представлена ​​в виде объекта, но которая имеет смысл только в контексте другого объекта, который не обязательно должен подвергаться воздействию внешнего мира, и который может извлечь выгоду из наличия доступа к данные родительских классов (чтобы не нарушать инкапсуляцию).

Лучший пример, который я могу придумать, - это поместить класс Node в LinkedList. Узлы имеют значение только для LinkedList, поэтому они существуют только в одном. Никто за пределами LinkedList не заботится об узлах и не должен иметь к ним доступ.

1 голос
/ 04 декабря 2012

Один из вариантов использования внутреннего класса:

Внутренний класс помогает в множественном наследовании. Внутренний класс позволяет наследовать от нескольких неинтерфейсов .

// первый случай;можно реализовать, если два класса являются интерфейсом

interface A {  }
interface B {  }

class X implements A, B { }

// второй случай;Вы можете продлить только один класс.Этот внутренний класс может помочь наследовать и другой класс

 class D {  }
 abstract class E { }
 class Z extends D {
    void method() {
      return new E()  {   };   //Anonymous inner class
    }
 }
1 голос
/ 29 октября 2010

Также, как вы знаете, в Java существуют вложенные классы, которые являются статическими внутренними объектами.

Из предыдущих постов становится ясно, когда нам нужно использовать внутренний класс, но я думаю, что вас также интересует вопрос "Почему мынужны вложенные классы (статический внутренний класс) ".

Ответ прост: есть та же цель, что и для внутреннего класса, за исключением нескольких вещей.

1) Вложенный класс (static inner) требуется, когда мы хотим исключить некоторую логику, котораякасается другого объекта, но эта логика может использоваться во внешнем мире.

Простейшие примеры - это построители или редакторы какого-либо объекта.Например, у нас есть класс Foo, в котором может быть много необязательных полей, для создания такого объекта мы можем решить ввести класс построителя, который будет выполнять эту работу.

    public class Foo {
    private int param1;
    private int param2;
    private int param3;

    private Foo(FooBuilder builder) {
        this.param1 = builder.param1;
        this.param2 = builder.param2;
        this.param3 = builder.param3;
    }

    public int getParam1() {
        return param1;
    }

    public void setParam1(int param1) {
        this.param1 = param1;
    }

    public int getParam2() {
        return param2;
    }

    public void setParam2(int param2) {
        this.param2 = param2;
    }

    public int getParam3() {
        return param3;
    }

    public void setParam3(int param3) {
        this.param3 = param3;
    }

    public static class FooBuilder {
        private int param1;
        private int param2;
        private int param3;

        public FooBuilder() {
        }

        public FooBuilder withParameter1(int param1) {
            this.param1 = param1;
            return this;
        }

        public FooBuilder withParameter2(int param2) {
            this.param2 = param2;
            return this;
        }

        public FooBuilder withParameter3(int param3) {
            this.param3 = param3;
            return this;
        }

        public Foo build() {
            return new Foo(this);
        }
    }
}

Этот пример иллюстрирует, по крайней мере, одну причину, почемунам нужны такие классы

2) Второе различие между внутренним и статическим внутренними классами состоит в том, что у первого всегда есть указатель на родительский класс.На самом деле компилятор создает синтетический элемент поля для нестатического внутреннего класса типа его родителя, именно поэтому мы можем получить доступ к закрытым членам родительского класса.Статическое внутреннее условие не имеет такого сгенерированного члена поля.Например, у нас есть просто простой родительский класс с объявленным нестатическим внутренним классом:

public class Foo {
    public class FooBuilder {
    }
}

, но на самом деле, если принять во внимание байт-код, он выглядит так:

public class Foo {
    public class FooBuilder {
        private Foo generatedNameHere;
    }
}

, если вы хотитеВы можете выяснить этот сгенерированный байтовый код.

1 голос
/ 29 октября 2010

Внутренний класс позволяет нам удалить эту логику и поместить ее в свой собственный класс.Таким образом, с объектно-ориентированной точки зрения, мы взяли функциональность там, где она не принадлежит, и поместили ее в свой собственный класс.

Пожалуйста, перейдите по этой ссылке ....

http://www.javaworld.com/javaworld/javaqa/2000-03/02-qa-innerclass.html

0 голосов
/ 10 декабря 2013
  1. С помощью внутренних классов вы можете получить доступ к закрытым членам включающего класса.
  2. Они полезны для реализаций интерфейса, которые используются только включающим классом (обработчиками событий в приложении).
  3. Они полезны для обеспечения детального доступа и управления созданием реализации интерфейса, которая извлекается извне (возможно, что-то вроде реализации Iterator).
0 голосов
/ 29 октября 2010
  1. Когда вы хотите указать класс, который имеет смысл только в контексте с ограниченным.

    Например, вы пишете класс MathOperations, который может выполнять четыре операции.Таким образом, операции могут быть представлены как внутренние перечисления MathOps.

  2. Когда внутренний класс не используется нигде, кроме ограниченного.анонимные внутренние классы для указания только операции, например, если вы хотите отсортировать коллекцию, вы указываете класс Comparable только для сравнения одного метода.

      Collections.sort(employments, new Comparator<Employment>() {
    
    
    <pre><code>    @Override
        public int compare(Employment o1, Employment o2) {
            return o1.getStartDate().before(o2.getStartDate()) ? 1 : -1 ;
        }
    });
    
...