Свойство (программирование)

Материал из Википедии — свободной энциклопедии
Перейти к навигации Перейти к поиску

Ошибка скрипта: Модуля «hatnote» не существует.{{#if: | }} Шаблон:Нет ссылок

Свойство — способ доступа к внутреннему состоянию объекта, имитирующий переменную некоторого типа. Обращение к свойству объекта выглядит так же, как и обращение к структурному полю (в структурном программировании), но, в действительности, реализовано через вызов функции. При попытке задать значение данного свойства вызывается один метод, а при попытке получить значение данного свойства — другой.

При применении свойств

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

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

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

Методы свойств

Во многих языках программирования свойства реализуются в виде пары методов: метод, получающий текущее значение свойства, называется акцессор (accessor); метод, задающий новое значение свойства, — мутатор (mutator).Шаблон:Нет АИ В языках программирования, не поддерживающих свойства, например, C++ и Java, пара из акцессора и мутатора является общепринятым суррогатом для их замены.

Принято называть методы свойств именем свойства с приставками get и set: например, для свойства Xyzzy — get_Xyzzy и set_Xyzzy (традиционный стиль Си) либо GetXyzzy и SetXyzzy (стиль CamelCase). В связи с этой схемой наименования за методами свойств закрепились жаргонные названия getter и setter.

Примеры

Свойства в C#

Свойства в C# — поля с логическим блоком, в котором есть ключевые слова get и set.

Пример класса со свойством: <source lang=csharp> class MyClass {

   private int p_field;
   public int Field
   {
       get
       {
           return p_field;
       }
       private set
       {
           p_field = value;
       }
   }

} </source>

Свойства в VB.NET

Пример реализации в VB.NET. Если нужно реализовать свойство только для чтения или только для записи, применяются модификаторы ReadOnly и WriteOnly. Свойство может быть параметризованным. Также может быть свойством по умолчанию, для этого необходимо добавить модификатор Default <source lang=vbnet> Sub Main

   Dim F As New Foo
   F.Data = 5
   F.Item(0) = 5
   F(0) = 5                'Запись в свойство
   Console.WriteLine(F(0)) 'Чтение свойства

End Sub

Public Class Foo

   Private m_Data As Integer
   Private m_Arr() As Integer = {1, 2, 3, 4, 5}
   Public Property Data As Integer
       Set(Value As Integer) 'Сеттер
           m_Data = Value
       End Set
       Get
           Return m_Data 'Геттер
       End Get
   End Property
   Public Default Property Item(Param As Integer) As Integer 'Параметризованное свойство по умолчанию
       Set(Value As Integer)
           m_Arr(Param) = Value
       End Set
       Get
           Return m_Arr(Param)
       End Get
   End Property

End Class </source>

Свойства в Delphi

Для описания свойства в Delphi служит слово property.

Пример класса со свойством: <source lang=delphi>TMyClass = class private

 FMyField: Integer;
 procedure SetMyField(const Value: Integer);
 function GetMyField: Integer;

public

 property MyField: Integer read GetMyField write SetMyField;

end;

function TMyClass.GetMyField: Integer; begin

 Result := FMyField;

end;

procedure TMyClass.SetMyField(const Value: Integer); begin

 FMyField := Value;

end;</source>

Свойства в ActionScript

<source lang=actionscript> class MyClass {

   private _foo : int;
   
   public function get foo () : int {
        return _foo;
   }
   public function set foo (foo : int) : void {
        _foo = foo;
   }

} </source>

Свойства в Objective C

<source lang=objc> @interface Company : NSObject { NSString *var_name; }

@property(retain) NSString *var_name;

@end

@implementation Company

@synthesize var_name;

@end </source>

Свойства в Ruby

Описания свойства в Ruby ничем не отличается от описания метода. Например, для создания свойства duration у класса Song нужно описать методы duration и duration=(value) <source lang=ruby>class Song

 def duration
   @duration
 end
 def duration=(value)
   @duration = value
 end

end</source>

Однако простое обращение к внутренней переменной объекта может быть заменено на вызов метода attr_accessor :duration

<source lang=ruby>class Song

 attr_accessor :duration

end</source>

Более интересным будет пример создания свойства duration_in_minutes, которое будет возвращать или устанавливать время длительности в минутах:

<source lang=ruby>class Song

 def duration_in_minutes
   @duration/60.0
 end
 def duration_in_minutes=(value)
   @duration = (value*60).to_i
 end

end</source>

При этом изменение свойства duration_in_minutes повлияет на свойство duration. Например

<source lang=ruby>song = Song.new song.duration_in_minutes = 1.2 print song.duration # напечатает 72</source>

Свойства в Python

Набор методов с декораторами определяет способы работы со свойством (чтение, запись, удаление). Если какой-то из методов убрать (за исключением @property), теряется возможность работать со свойством соответствующим образом.

Пример класса со свойством: <source lang=python> class A:

   def __init__(self):
       self.__x = None
   
   @property
   def x(self):
       return self.__x
   
   @x.setter
   def x(self, value):
       self.__x = value
   
   @x.deleter
   def x(self):
       self.__x = None

</source>

<source lang=python> >>> a = A() >>> a.x >>> a.x = 2 >>> a.x 2 >>> del a.x >>> a.x >>> </source>

Свойства в PHP

Язык PHP предоставляет полноценные свойства (иначе именуемые "хуками" в рамках терминологии PHP), начиная с версии PHP 8.4.

Пример класса "статьи" со свойством "содержимое". В примере, для свойства содержимого добавляется функционал конвертации в строку при установке произвольного значения "похожего на строку": <source lang="php">class Article {

   public string $content =  {
       // Чтение: Просто возвращаем
       get => $this->content;
       // Запись: Позволяем устанавливать string скляры 
       //         и объекты, конвертирующиеся в string
       set(string|\Stringable $value) => (string) $value;
   }

}</source>

<source lang="php"> $article = new Article();

// Можем установить скалярный string // Срабатывает set $article->content = 'from string literal';

// Скаляр при выводе: string("from string literal") // Срабатывает get echo $article->content;

// Можем установить Stringable-объект // Срабатывает set $article->content = new class implements Stringable {

   public function __toString(): string
   {
       return 'from stringable object';
   }

};

// Тоже скаляр при выводе: string("from stringable object") // Срабатывает get echo $article->content; </source>

См. также