Подтвердить что ты не робот

Какова цель ключевого слова 'this' в С#

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

private static class SomeClass : ISomeClass
{
    private string variablename;
    private void SomeMethod(string toConcat)
    {
        this.variablename = toConcat+toConcat;
        return this.variablename;
    }
}

Когда это будет делать то же самое:

private static class SomeClass : ISomeClass
{
    private string variablename;
    private void SomeMethod(string toConcat)
    {
        variablename = toConcat+toConcat;
        return variablename;
    }
}

чтобы практиковать свои навыки набора текста?

4b9b3361

Ответ 1

Есть несколько случаев, когда это имеет значение:

  • Если у вас есть параметр функции и переменная-член с одинаковыми именами, вы должны иметь возможность различать их:

    class Foo {
      public Foo(int i) { this.i = i; }
    
      private int i;
    }
    
  • Если вам действительно нужно ссылаться на текущий объект, а не на один из его членов. Возможно, вам нужно передать его другой функции:

    class Foo {
      public static DoSomething(Bar b) {...}
    }
    
    class Bar {
      public Bar() { Foo.DoSomething(this); }
    }
    

    Конечно же, если вы хотите вернуть ссылку на текущий объект

Ответ 2

В вашем примере это чисто дело вкуса, но вот случай, когда это не так:

private string SomeMethod(string variablename)
{
    this.variablename = variablename;
    return this.variablename;
}

Без this, код будет работать по-другому, присваивая параметр самому себе.

Ответ 3

Есть много случаев, когда это полезно. Вот один пример:

class Logger { 
   static public void OutputLog (object someObj) {
      ...
   }
}

class SomeClass { 
   private void SomeMethod () { 
      Logger.OutputLog (this);
   } 
}

Вот еще один пример. Предположим, что я писал метод Stream.Out, который выводит объект и возвращает ссылку на сам поток, например:

class Stream {
   public Stream Out (object obj) { 
      ... code to output obj ...
      return this; 
   }
}

Затем можно использовать этот вызов Out в цепном режиме:

Stream S = new Stream (...);
S.Out (A). Out (B). Out (C);

Ответ 4

В дополнение к ответам "полевые неоднозначности" и "передаче ссылки текущего isntance" (уже задано) существует дополнительный сценарий, где this необходим; для вызова методов расширения в текущем экземпляре (я игнорирую использование this в объявлении метода расширения, поскольку это не совсем то же самое значение, что и вопрос):

class Foo
{
    public void Bar()
    {
        this.ExtnMethod(); // fine
        ExtnMethod(); // compile error
    }
}
static class FooExt
{
    public static void ExtnMethod(this Foo foo) {}
}

Чтобы быть справедливым, это не общий сценарий. Скорее всего, это просто сделать код более читаемым, например:

public bool Equals(Foo other) {
    return other != null && this.X == other.X && this.Y == other.Y;
}

В приведенном выше (или аналогично для Compare, Clone и т.д.) без this. я нахожу его немного... "неуравновешенным".

Ответ 5

Вам нужен this, если ваш параметр метода имеет то же имя, что и поле.

private string variablename;
private void SomeMethod(string variablename)
{
    this.variablename = variablename+variablename;
    return this.variablename;
}

Ответ 6

В большинстве случаев использование this просто загромождает код. Тем не менее, я видел, как он использовался другими программистами, предположительно для запуска intellisense для членов локального класса.

Ключевое слово this также требуется для использования в методах расширения.

public static class MyExtensions
{
    public static int WordCount(this String str)
    {
        return str.Split(new char[] { ' ', '.', '?' }, StringSplitOptions.RemoveEmptyEntries).Length;
    }
}  

Ответ 7

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

Независимо, this - это просто ссылка на текущий экземпляр. Он может использоваться для разрешения конфликтов между локальными переменными и переменными-членами, например:

public class Foo
{
    private string baz;

    public void Bar(string baz)
    {
        this.baz = baz;
    }
}

Его также можно использовать просто как самостоятельный объект, например:

public class Foo
{
    public List<Foo> GetList(string baz)
    {
        var list = new List<Foo>();
        list.Add(this);

        return list;
    }
}

(Не то, чтобы этот пример особенно полезен, но вы получаете идею.)

Изменить: Более реалистичным примером является модель событий в .NET:

public class Foo
{
    public EventHandler SomeEvent;

    public void Bar()
    {
        if (SomeEvent != null)
        {
            SomeEvent(this, EventArgs.Empty);
        }
    }
}

Ответ 8

  • this означает ваш текущий экземпляр класса экземпляра, а не
    а. ваш базовый член класса
    б. член области
    с. статический член
  • Чтобы сделать ваш код более читаемым.

Ответ 9

Первое, что приходит мне в голову, - это читаемость и/или личные предпочтения.

Иногда, когда я работаю с довольно большим классом... или классом с базовым классом (где я не могу "видеть" некоторые переменные)... Я использую ключевое слово "this"... как минимум для intellisense в Visual Studio.

Ответ 10

За пределами, возможно, Javascript, "this" в основном является ключевым словарем-заполнителем, и наиболее полезно сделать ваше намерение очевидным при написании фрагмента кода.

В основном это поможет с удобочитаемостью.

Ответ 11

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

Например:

class Image
{
    void Refresh()
    {
        Screen.DrawImage(this);
    }
}

В отличие от некоторых других сценариев, где использование или отсутствие использования этого ". является вопросом стиля или средством разрешения искусственной двусмысленности.

Ответ 12

Я почтительно не согласен с некоторыми другими плакатами. В С# это не просто вопрос вкуса; он также соответствует руководящим принципам Microsoft С# (как внутри, так и снаружи, хотя они, похоже, не соответствуют их собственным принципам внутри).

Есть примеры случаев, когда используемая вами нотация не будет работать:

private void DoSomething(object input) 
{ 
    input = input; 
} 

Вместо этого вам нужно будет использовать следующие обозначения:

private void DoSomething(object input) 
{ 
    this.input = input; 
} 

Ответ 13

this относится к экземпляру класса, и в примере, который вы нам показываете: вы используете this для ссылки на поле под названием variablename.

Если у вас есть локальная переменная или параметр с тем же именем, вам нужно будет различать между ними. В этом случае this будет ссылаться на поле, а не на префикс с this ссылается на локальную переменную или параметр.

У вас должно быть соглашение об именах, которое поможет вам различать поля и локальные жители. Это избавит вас от проблем, которые могут возникнуть, если позднее вы добавите локальное имя с таким же именем в свой метод. (Так как код без this будет прерывать...)

Ответ 14

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

Ответ 15

Обычно используется аргумент конструктора с тем же именем:

public SomeClass(string variablename)
{
   this.variablename = variablename;
}

Ответ 16

1) Во-первых, и самое главное, это ситуация, когда объект должен передать ссылку себе:

public class Element{
//...
public Element Parent;
public Element Root()
{
 if( Parent == null )
  return this;
 return Parent.Root();
}
}
public void OnEvent()
{
 Event(this, new EventArgs());
}

В свободном интерфейсе:

public class Query {  public Query Add (параметр параметра) {_list.Add(параметр); верните это; } }

2) Во-вторых, метод in и extension:

public class Extension
{
 public Element Root(this Element element) {
  if( element.Parent == null )
   return element;
  return element.Parent.Root();
 }
}

3) В-третьих, вам это действительно не нужно, чтобы отличать параметры от членов класса. Это вам не нужно, потому что хорошее соглашение о кодировании избавляет вас от использования ключевого слова 'this'.

public class Element
{
 public Element Parent;
 publlc void SetParent(Element parent)
 {
   // this.Parent = parent; // see, you don't need it
   Parent = parent;
 }
}
//...
public class Element
{
 public Element _parent;
 public Element Parent { get { return _parent; } }
 publlc void SetParent(Element parent)
 {
   // this._parent = parent; // see, you don't need it
   _parent = parent;
 }
}

Ответ 17

Существует один принцип, который должен помочь вам решить, использовать или не использовать 'this'. Вам нужно конкретно обратиться к ЭТОУ экземпляру класса? Если вы это сделаете, используйте 'this'. В противном случае оставьте это.

Примером этого может служить пример Logger другого плаката. Он не мог полагаться на неявное это, поскольку ему нужен был сам объект.

Нет смысла использовать 'this' в качестве префикса для метода самого класса, в самом классе, поскольку он неявный.

Ответ 18

Я не могу не...

if (this == null)
    throw new NullReferenceException();

[KIDDDIIIING!!!]

Ответ 19

Другой сценарий, который я уже нашел:

private int value;
public int Value
{
    get { return this.value; }
    set { this.value = value; } //without this it doesn't make sense
}