Домашнее задание: сравнение даты [дубликат]

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

Предположим, что у вас есть класс с именем Student.

public class Student
{
    private string FirstName;
    private string LastName;
    public string GetFullName()
    {
        return FirstName + LastName;
    }
}

Теперь рассмотрим другой класс, в котором вы пытаетесь получить полное имя учащегося.

public class StudentInfo
{      
    public string GetStudentName()
    {
        Student s;
        string fullname = s.GetFullName();
        return fullname;
    }        
}

Как видно из вышеприведенного кода, оператор Student s - объявляет только переменную типа Student, обратите внимание, что класс Student не создается в этой точке. Следовательно, когда выполняется выполнение инструкции s.GetFullName (), она выкинет исключение NullReferenceException.

190
задан Gabriel Ščerbák 27 April 2010 в 09:37
поделиться

17 ответов

Единственная необходимость использовать квалификатор this. - это когда другая переменная в текущей области имеет одно имя и вы хотите обратиться к члену экземпляра (как описывает Уильям). Кроме того, нет разницы в поведении между x и this.x.

20
ответ дан Adam Robinson 27 August 2018 в 15:13
поделиться
  • 1
    И если у вас есть повторяющиеся имена, одна из ваших переменных должна быть переименована, поскольку ее почти однозначно называют неправильно. Или, по крайней мере, можно назвать лучше. – CaffGeek 9 March 2010 в 19:12
  • 2
    @Chad: Это обычная практика в методах настройки Java. Однако, помимо методов setter, ваши утверждения обычно сохраняются. – William Brendel 9 March 2010 в 19:14
  • 3
    Возможно, вы захотите использовать this.x, чтобы ваш код читался немного более четко, а также удобство и удобочитаемость кода также является фактором, который вы должны учитывать ... – Bryan Rehbein 9 March 2010 в 19:14
  • 4
    @Chad: Я не могу согласиться с энтузиазмом. Господи, только потому, что «это». позволяет вам указать две разные переменные с одинаковым именем, для чего вы ХОТИТЕ? – BlairHippo 9 March 2010 в 19:15
  • 5
    @Blair: Чтение вашего ответа дает понять, что вы не предпочитаете эту практику в методах setter, но многие люди (я бы включил себя в этот список). Если у меня есть метод сеттера, который принимает значение, то явно переданное значение должно быть «новым». значение, поэтому добавление "новых" к имени переменной, кажется, добавляет излишнюю избыточность к публичному API. – Adam Robinson 9 March 2010 в 19:17

Что касается сообщений Уильяма Бренделя и dbconfessions , в отношении случая 2. Вот пример:

public class Window {

  private Window parent;

  public Window (Window parent) {
    this.parent = parent;
  }

  public void addSubWindow() {
    Window child = new Window(this);
    list.add(child);
  }

  public void printInfo() {
    if (parent == null) {
      System.out.println("root");
    } else {
      System.out.println("child");
    }
  }

}

I ' Видно, что это использовалось при построении отношений родитель-ребенок с объектами. Однако, пожалуйста, учтите, что для краткости это упрощено.

0
ответ дан Alija 27 August 2018 в 15:13
поделиться

Будет ли какая-либо разница, если я использую «x» вместо «this.x» в некоторых методах?

Обычно нет. Но иногда это имеет значение:

  class A {
     private int i;
     public A(int i) {
        this.i = i; // this.i can be used to disambiguate the i being referred to
     }
  }

Если я просто использую метод (), не будет ли он по умолчанию применяться к текущему объекту?

Да. Но при необходимости this.method() разъясняет, что вызов выполняется этим объектом.

0
ответ дан amit_grepclub 27 August 2018 в 15:13
поделиться

this полезен в шаблоне построителя.

public class User {

    private String firstName;
    private String surname;

    public User(Builder builder){
        firstName = builder.firstName;
        surname = builder.surname;
    }

    public String getFirstName(){
        return firstName;
    }

    public String getSurname(){
        return surname;
    }

    public static class Builder {
        private String firstName;
        private String surname;

        public Builder setFirstName(String firstName) {
            this.firstName = firstName;
            return this;
        }

        public Builder setSurname(String surname) {
            this.surname = surname;
            return this;
        }

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

    }

    public static void main(String[] args) {
        User.Builder builder = new User.Builder();
        User user = builder.setFirstName("John").setSurname("Doe").build();
    }

}
9
ответ дан andrzej.szmukala 27 August 2018 в 15:13
поделиться
  • 1
    Это был тот тип ответа, который я хотел, когда я искал и заканчивал здесь, но у вас нет объяснения вашего кода, поэтому большинство людей, которые спрашивают об этом «,», не поймут, что «вернуть нового пользователя» (это) ; & Quot; значит, как я не ... – nckbrz 11 April 2014 в 22:25
  • 2
    Шаблон Builder используется для четкого определения параметров конструкции. Вместо того, чтобы иметь новый User (string, string) без простого способа указать, какая строка была, у вас будет новый Builder (). SetFirstName (& quot; Jane & quot;). SetSurname (& quot; Smith & quot;). Build (). Вы возвращаете это из функций Builder.set ... (), чтобы их можно было связать. – ChrisPhoenix 7 September 2015 в 23:43

«this» также полезно при вызове одного конструктора из другого:

public class MyClass {
    public MyClass(String foo) {
        this(foo, null);
    }
    public MyClass(String foo, String bar) {
        ...
    }
}
15
ответ дан Benjamin 27 August 2018 в 15:13
поделиться

Google поднял страницу на сайте Sun, которая немного обсуждает это.

Вы правы в переменной; this действительно может использоваться для дифференциации переменной метода из поля класса. [f1]

Однако, я действительно ненавижу это соглашение. Предоставление двух разных переменных буквально одинаковых имен - это рецепт ошибок. Я предпочитаю что-то вроде: [f2]

Те же результаты, но без шансов на ошибку, когда вы случайно ссылаетесь на x, когда вы действительно хотели ссылаться на x.

Что касается использования этого метода, вы правы в отношении эффектов; вы получите те же результаты с или без него. Вы можете использовать его? Конечно. Должны ли вы использовать его? До вас, но, учитывая, что я лично считаю бессмысленной многословность, которая не добавляет ясности (если код не заполнен статическими операторами импорта), я не склонен использовать его сам.

3
ответ дан BlairHippo 27 August 2018 в 15:13
поделиться
  • 1
    Это не конвенция, это механизм определения языка программы. То, что вы указали, - использование newX (я предпочитаю pX для параметра x) - это соглашение. – Bill K 9 March 2010 в 19:13
  • 2
    @Bill K: Я не понимаю различия, которые вы делаете. Я могу выбрать имя переменной ввода x, или newX, или pX, или mangroveThroatWarblerX. Как выбрать, чтобы дать ему имя, идентичное переменной, которую он устанавливает, не является соглашением, в то время как добавление "новых" или "p" или «Безвозмездные ссылки на Монти Питон»). Соглашения ARE? – BlairHippo 9 March 2010 в 19:20
  • 3
    & quot; Gratuitoud Monty Python References & quot; это не конвенция, это ЗАКОН. – Adam Robinson 9 March 2010 в 19:23
  • 4
    +1: По этой причине мы используем другой стандарт именования для аргументов и переменных метода, чем для переменных класса. Мы сокращаем аргументы / методы vars и используем полные слова для переменных класса / экземпляра. – Lawrence Dol 9 March 2010 в 20:23
  • 5
    Решить его, используя соглашение об именах, это хм, соглашение. Решая его с помощью языковой функции - я думаю, что выбор никогда не использовать эту функцию языка или всегда использовать ее будет конвенцией ... Используя это. каждый раз, когда вы получаете доступ к члену, это соглашение. Думаю, это не имеет большого значения, я ненавижу это. – Bill K 10 March 2010 в 02:44

Если у вас нет совпадающих имен переменных, это действительно просто для ясности, когда вы читаете код.

6
ответ дан ChickenMilkBomb 27 August 2018 в 15:13
поделиться
  • 1
    Или беспорядок ..... – Steve Kuo 10 March 2010 в 02:03
  • 2
    Когда вы постоянно видите ключевое слово this, когда это необязательно, это просто код шаблона, который делает код более трудным для чтения. – AxeEffect 8 October 2013 в 01:21
  • 3
    Я просто наткнулся на проект с открытым исходным кодом, который требует, чтобы члены all имели префикс «this». Кроме того, проект очень хорошо написан, но у меня возникает соблазн попасть в религиозные дебаты с ними. – LegendLength 12 October 2017 в 14:41
  • 4
    @AxeEffect Я знаю, что это действительно старый, но ... this НЕ делает код сложнее читать lmao. – Xatenev 14 November 2017 в 15:45

Второе важное использование this (помимо скрытия с локальной переменной, о чем уже говорят многие ответы) - это обращение к внешнему экземпляру из вложенного нестатического класса:

public class Outer {
  protected int a;

  public class Inner {
    protected int a;

    public int foo(){
      return Outer.this.a;
    }

    public Outer getOuter(){
      return Outer.this;
    }
  }
}
60
ответ дан Christopher Oezbek 27 August 2018 в 15:13
поделиться

this не влияет на итоговый код - это оператор времени компиляции, и код, сгенерированный с ним или без него, будет таким же. Когда вы должны использовать его, зависит от контекста. Например, вы должны использовать его, как вы сказали, когда у вас есть локальная переменная, которая изменяет переменную класса, и вы хотите ссылаться на переменную класса, а не на локальную.

изменить: по «результирующий код будет тот же «Я имею в виду, конечно, когда какая-то переменная в локальной области не скрывает того, что принадлежит классу. Таким образом,

class POJO {
   protected int i;

   public void modify() {
      i = 9;
   }

   public void thisModify() {
      this.i = 9;
   }
}

полученный код обоих методов будет таким же. Разница будет в том, что если какой-либо метод объявляет локальную переменную с тем же именем

  public void m() {
      int i;
      i = 9;  // i refers to variable in method's scope
      this.i = 9; // i refers to class variable
  }
0
ответ дан doc 27 August 2018 в 15:13
поделиться

Вам нужно использовать this - и большинство людей используют его только при наличии локальной локальной переменной с таким же именем. (Например, методы сеттера.)

Конечно, еще одна веская причина использовать this в том, что она вызывает всплытие intellisense в IDE:)

39
ответ дан froadie 27 August 2018 в 15:13
поделиться
  • 1
    +1 intellisense, yay за ленивый :) – Tanzelax 9 March 2010 в 19:47
  • 2
    Но тогда вы должны отменить его после того, как вы его просмотрите. Программирование утомительно! – LegendLength 12 October 2017 в 14:32

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

1
ответ дан giri 27 August 2018 в 15:13
поделиться

Есть много хороших ответов, но есть еще одна очень небольшая причина, чтобы поместить this всюду. Если вы попытались открыть исходные коды из обычного текстового редактора (например, блокнот и т. Д.), Использование this сделает его более понятным для чтения.

Представьте это:

public class Hello {
    private String foo;

    // Some 10k lines of codes

    private String getStringFromSomewhere() {
        // ....
    }

    // More codes

    public class World {
        private String bar;

        // Another 10k lines of codes

        public void doSomething() {
            // More codes
            foo = "FOO";
            // More codes
            String s = getStringFromSomewhere();
            // More codes
            bar = s;
        }
    }
}

Это очень понятно для чтения с любой современной IDE, но это будет полный кошмар для чтения с помощью обычного текстового редактора.

Вам будет трудно узнать, где находится foo, пока вы не используйте функцию «Найти» редактора. Тогда вы будете кричать на getStringFromSomewhere() по той же причине. Наконец, после того, как вы забыли, что s есть, bar = s даст вам последний удар.

Сравните это с этим:

public void doSomething() {
    // More codes
    Hello.this.foo = "FOO";
    // More codes
    String s = Hello.this.getStringFromSomewhere();
    // More codes
    this.bar = s;
}
  1. Вы знаете, что foo - переменная, объявленная во внешнем классе Hello.
  2. Вы знаете, что getStringFromSomewhere() - это метод, объявленный также в внешнем классе.
  3. Вы знаете, что bar принадлежит классу World, а s - локальная переменная, объявленная в этом методе.

Конечно, всякий раз, когда вы что-то создаете, вы создаете правила. Поэтому при разработке вашего API или проекта, если ваши правила включают «если кто-то открывает все эти исходники с помощью блокнота, он или она должен стрелять в себя в голову», тогда вы совершенно не хотите делать это .

2
ответ дан Jai 27 August 2018 в 15:13
поделиться

Ключевое слово this используется в основном в трех ситуациях. Первый и наиболее распространенный в методах setter для устранения неоднозначности ссылок на переменные. Во-вторых, когда необходимо передать текущий экземпляр класса в качестве аргумента методу другого объекта. Третий - это способ вызова альтернативных конструкторов из конструктора.

Случай 1: Использование this для устранения неоднозначности ссылок на переменные. В методах настройки Java мы обычно передаем аргумент с тем же именем, что и переменная частного члена, которую мы пытаемся установить. Затем мы назначим аргумент x на this.x. Это дает понять, что вы присваиваете значение параметра «name» переменной экземпляра «name».

public class Foo
{
    private String name;

    public void setName(String name) {
        this.name = name;
    }
}

Случай 2: Использование this в качестве аргумента, переданного другому объекту.

public class Foo
{
    public String useBarMethod() {
        Bar theBar = new Bar();
        return theBar.barMethod(this);
    }

    public String getName() {
        return "Foo";
    }
}

public class Bar
{
    public void barMethod(Foo obj) {
        obj.getName();
    }
}

Случай 3: Использование this для вызова альтернативных конструкторов. В комментариях trinithis правильно указал еще одно общее использование this. Когда у вас есть несколько конструкторов для одного класса, вы можете использовать this(arg0, arg1, ...) для вызова другого конструктора по вашему выбору, если вы делаете это в первой строке своего конструктора.

class Foo
{
    public Foo() {
        this("Some default value for bar");

        //optional other lines
    }

    public Foo(String bar) {
        // Do something with bar
    }
}

Я также видел this используется для того, чтобы подчеркнуть тот факт, что на переменную экземпляра ссылаются (без необходимости устранения неоднозначности), но это редкий случай, на мой взгляд.

271
ответ дан Michael 27 August 2018 в 15:13
поделиться
  • 1
    +1 Заметим, что вы также можете передать this в качестве аргумента. этот используется не только для устранения неоднозначности объема. – Alexandre Jasmin 9 March 2010 в 19:24
  • 2
    Конечно, внутри конструктора есть this(arg1, arg2, ...). – Thomas Eding 9 March 2010 в 19:41
  • 3
    @Hazior: Я склонен писать короткий ответ, а затем добавляю к нему со временем. Иногда это перекрывается с ответами других людей, иногда нет. В случае с моим последним правлением тринити указал на другое общее использование this, которое я забыл, поэтому я добавил его к моему ответу. Я не вижу в этом ничего плохого, потому что конечный результат - лучший ответ в целом, что является целью SO. Я также стараюсь давать кредит там, где это возможно, как это было в случае с тринитисом. – William Brendel 9 March 2010 в 22:12
  • 4
    У вас есть примеры для случаев 1 и 3. Не могли бы вы привести пример случая 2, в котором текущий экземпляр класса используется в качестве аргумента для метода другого класса? – dbconfession 11 September 2014 в 22:40
  • 5
    @AStar В большинстве Java-кодов, с которыми я работал в течение многих лет, this используется только в том случае, если необходимость в значении действительно необходима, например, в приведенном выше примере сеттера. Стили стилей и «лучшие практики». может сильно варьироваться в зависимости от того, кого вы спрашиваете, конечно, но в целом я рекомендую выбирать разумные шаблоны и придерживаться их. Согласованность, даже внутренне внутри одной кодовой базы, имеет большой путь к удобочитаемости и ремонтопригодности. – William Brendel 26 February 2016 в 06:06

Чтобы убедиться, что используются элементы текущего объекта. Случаи, связанные с безопасностью потоков, некоторые приложения могут изменять неправильные значения элементов объектов, поэтому это должно быть применено к элементу, чтобы использовать правильное значение члена объекта.

Если ваш объект не является связанные с безопасностью потоков, тогда нет никаких оснований указывать, какое значение имеет значение члена объекта.

-7
ответ дан Myster October 27 August 2018 в 15:13
поделиться
  • 1
    Это действительно не так. Я даже не уверен, в каком случае вы думаете, но пример может быть полезен для понимания того, что вы пытаетесь сказать. – David Berger 12 March 2010 в 00:54
  • 2
    Да. Я знаю, что вы объясняете, это вопрос безопасности потоков. На этот вопрос нет правильного ответа, который подразумевает безопасность потоков. Если "этот" необходимо ссылаться на правильный объект, а затем, как только он это сделает, метод или атрибут будут потокобезопасными тогда и только тогда, когда они синхронизированы. Если ссылка не является двусмысленной, она будет неоднозначной, если проблема многопоточности. – David Berger 10 May 2012 в 00:30

Ответ @William Brendel предоставил три разных варианта использования красивым способом.

Использовать случай 1:

В документации по документации java на этот предоставляет те же варианты использования.

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

Он охватывает два примера:

Используя это с полем и Используя это с конструктором

Используйте случай 2:

Другой вариант использования, который имеет не цитируется в этом сообщении: this может использоваться для синхронизации текущего объекта в многопоточном приложении для защиты критического раздела данных & amp; методы.

synchronized(this){
    // Do some thing. 
}

Использовать случай 3:

Реализация шаблона Builder зависит от использования this для возврата измененный объект.

См. этот пост

Сохранение строителя в отдельном классе (свободный интерфейс)

3
ответ дан Ravindra babu 27 August 2018 в 15:13
поделиться

Ниже приведены способы использования этого ключевого слова в java:

  1. Использование ключевого слова this для ссылки на текущие переменные экземпляра класса
  2. Использование this() для вызова конструктор текущего класса
  3. Использование ключевого слова this для возврата текущего экземпляра класса
  4. Использование ключевого слова this в качестве параметра метода

https://docs.oracle.com/javase/tutorial/java/javaOO/thiskey.html

1
ответ дан roottraveller 27 August 2018 в 15:13
поделиться

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

public class circle {
    int x;
    circle(int x){
        this.x =x;
        //class variable =local variable 
    }
} 

this также может использоваться для вызова одного конструктора из другого конструктора. например:

public class circle {
    int x;

    circle() { 
        this(1);
    }

    circle(int x) {
        this.x = x; 
    }
}
1
ответ дан Sven-Michael Stübe 27 August 2018 в 15:13
поделиться
Другие вопросы по тегам:

Похожие вопросы: