Wiązanie nazwy - Name binding
W językach programowania , nazwa wiązania jest stowarzyszenie podmiotów (dane i / lub kod) z identyfikatorami . Mówi się, że identyfikator powiązany z obiektem odwołuje się do tego obiektu. Języki maszynowe nie mają wbudowanego pojęcia identyfikatorów, ale powiązania nazwa-obiekt jako usługa i notacja dla programisty są implementowane przez języki programowania. Wiązanie jest ściśle związane z określaniem zakresu , ponieważ zakres określa, które nazwy wiążą się z jakimi obiektami – w jakich miejscach w kodzie programu ( leksykalnie ) iw której z możliwych ścieżek wykonania ( czasowo ).
Użycie identyfikatora id
w kontekście, który ustanawia powiązanie dla, id
nazywa się wystąpieniem powiązania (lub zdefiniowaniem). We wszystkich innych wystąpieniach (np. w wyrażeniach, przypisaniach i wywołaniach podprogramów) identyfikator oznacza to, z czym jest związany; takie wystąpienia są nazywane wystąpieniami zastosowanymi.
Czas wiązania
- Wiązanie statyczne (lub wczesne wiązanie ) to wiązanie nazwy wykonywane przed uruchomieniem programu.
- Wiązanie dynamiczne (lub późne wiązanie lub wiązanie wirtualne ) to wiązanie nazwy wykonywane podczas działania programu.
Przykładem powiązania statycznego jest bezpośrednie wywołanie funkcji w języku C : funkcja, do której odwołuje się identyfikator, nie może ulec zmianie w czasie wykonywania.
Ale przykładem dynamicznego wiązania jest dynamic dispatch , tak jak w C++ wywołaniu metody wirtualnej. Ponieważ konkretny typ obiektu polimorficznego nie jest znany przed uruchomieniem (ogólnie), wykonywana funkcja jest dynamicznie powiązana. Weźmy na przykład następujący kod Java :
public void foo(java.util.List<String> list) {
list.add("bar");
}
List
jest interfejsem , więc list
musi odnosić się do jego podtypu . Jest to odniesienie do LinkedList
An ArrayList
, lub jakiś inny podtyp z List
? Rzeczywista metoda, do której odwołuje się, add
nie jest znana do czasu wykonywania. W języku C takie wystąpienie dynamicznego wiązania może być wywołaniem funkcji wskazywanej przez zmienną lub wyrażenie typu wskaźnika funkcji, którego wartość jest nieznana, dopóki nie zostanie oceniona w czasie wykonywania.
Rebinding i mutacja
Rebindingu nie należy mylić z mutacją.
- Ponowne wiązanie to zmiana identyfikatora odniesienia .
- Mutacja to zmiana w encji, do której się odwołujemy .
Rozważmy następujący kod Java :
LinkedList<String> list;
list = new LinkedList<String>();
list.add("foo");
list = null;
Identyfikator list
początkowo nie odwołuje się do niczego (jest niezainicjowany ); następnie jest odbity, aby odnieść się do obiektu (połączonej listy ciągów). Połączona lista, do której odwołuje się, list
jest następnie mutowana, dodając ciąg do listy. Wreszcie list
odbicia do null
.
Późne zakłócenia
Późne wiązanie statyczne to wariant wiązania gdzieś pomiędzy wiązaniem statycznym a dynamicznym. Rozważmy następujący przykład PHP :
class A
{
public static $word = "hello";
public static function hello() { print self::$word; }
}
class B extends A
{
public static $word = "bye";
}
B::hello();
W tym przykładzie interpreter PHP wiąże słowo kluczowe self
inside A::hello()
z class A
, a więc wywołanie to B::hello()
tworzy ciąg znaków "hello". Gdyby semantyka self::$word
opierała się na późnym wiązaniu statycznym, rezultatem byłoby „pa”.
Począwszy od wersji PHP 5.3 obsługiwane jest późne wiązanie statyczne. W szczególności, jeśli self::$word
w powyższym zostały zmienione na takie, static::$word
jak pokazano w poniższym bloku, gdzie słowo kluczowe static
byłoby powiązane tylko w czasie wykonywania, wynikiem wywołania to B::hello()
byłoby „bye”:
class A
{
public static $word = "hello";
public static function hello() { print static::$word; }
}
class B extends A
{
public static $word = "bye";
}
B::hello();
Zobacz też
- Późne wiązanie
- Metoda tabeli rozgałęzienia stosowania wiązania nazwy za pomocą tabeli rozgałęzienia lub wskaźników funkcji
- Dynamiczna wysyłka
- Składnia abstrakcyjna wyższego rzędu (HOAS)