Spec-Zone.ru › Elisp

Предикаты равенства

Здесь описываются функции, которые проверяют равенство двух объектов. Другие функции проверяют равенство содержимого между объектами определенных типов, например, строками. Для этих предикатов см. соответствующую главу, описывающую тип данных.

Функция: eq object1 object2

Эта функция возвращает t, если object1 и object2 являются одним и тем же объектом, и nil в противном случае.

Если object1 и object2 являются символами с одинаковым именем, они обычно являются одним и тем же объектом — но см. Создание символов для исключений. Для других типов, не являющихся числовыми (например, списки, векторы, строки), два аргумента с одинаковым содержимым или элементами не обязательно eq друг другу: они eq только в том случае, если они являются одним и тем же объектом, что означает, что изменение содержимого одного будет отражено тем же изменением содержимого другого.

Если object1 и object2 являются числами с разными типами или значениями, то они не могут быть одним и тем же объектом, и eq возвращает nil. Если они являются fixnums с одинаковым значением, то они являются одним и тем же объектом, и eq возвращает t. Если они были вычислены раздельно, но имеют одинаковое значение и одинаковый тип чисел, не являющихся fixnums, то они могут или не могут быть одним и тем же объектом, и eq возвращает t или nil, в зависимости от того, создал ли интерпретатор Lisp один объект или два.

(eq 'foo 'foo)
     ⇒ t
(eq ?A ?A)
     ⇒ t
(eq 3.0 3.0)
     ⇒ t or nil
;; Equal floats may or may not be the same object.
(eq (make-string 3 ?A) (make-string 3 ?A))
     ⇒ nil
(eq "asdf" "asdf")
     ⇒ t or nil
;; Equal string constants or may not be the same object.
(eq '(1 (2 (3))) '(1 (2 (3))))
     ⇒ nil
(setq foo '(1 (2 (3))))
     ⇒ (1 (2 (3)))
(eq foo foo)
     ⇒ t
(eq foo '(1 (2 (3))))
     ⇒ nil
(eq [(1 2) 3] [(1 2) 3])
     ⇒ nil
(eq (point-marker) (point-marker))
     ⇒ nil

Функция make-symbol возвращает неинтернированный символ, отличающийся от символа, который используется, если вы пишете имя в выражении Lisp. Различные символы с одинаковым именем не eq. См. Создание символов.

(eq (make-symbol "foo") 'foo)
     ⇒ nil

Компилятор байт-кода Emacs Lisp может объединять идентичные литеральные объекты, такие как литеральные строки, в ссылки на один и тот же объект, в результате чего скомпилированный байт-код будет сравнивать такие объекты как eq, в то время как интерпретируемая версия того же кода — нет. Поэтому ваш код никогда не должен полагаться на то, что объекты с одинаковым буквальным содержимым являются либо eq или не eq, вместо этого он должен использовать функции, которые сравнивают содержимое объектов, такие как equal, описанные ниже. Аналогично, ваш код не должен изменять литеральные объекты (например, добавлять текстовые свойства к литеральным строкам), так как это может повлиять на другие литеральные объекты с тем же содержимым, если компилятор байт-кода объединит их.

Функция: equal object1 object2

Эта функция возвращает t, если object1 и object2 имеют равные компоненты, и nil в противном случае. В то время как eq проверяет, являются ли ее аргументы одним и тем же объектом, equal смотрит внутри неидентичных аргументов, чтобы увидеть, являются ли их элементы или содержимое одинаковыми. Таким образом, если два объекта eq, они equal, но обратное не всегда верно.

(equal 'foo 'foo)
     ⇒ t
(equal 456 456)
     ⇒ t
(equal "asdf" "asdf")
     ⇒ t
(eq "asdf" "asdf")
     ⇒ nil
(equal '(1 (2 (3))) '(1 (2 (3))))
     ⇒ t
(eq '(1 (2 (3))) '(1 (2 (3))))
     ⇒ nil
(equal [(1 2) 3] [(1 2) 3])
     ⇒ t
(eq [(1 2) 3] [(1 2) 3])
     ⇒ nil
(equal (point-marker) (point-marker))
     ⇒ t
(eq (point-marker) (point-marker))
     ⇒ nil

Сравнение строк чувствительно к регистру, но не учитывает текстовые свойства — сравниваются только символы в строках. См. Текстовые свойства. Используйте equal-including-properties для сравнения текстовых свойств. По техническим причинам однобайтовая строка и многобайтовая строка являются equal, если и только если они содержат одну и ту же последовательность кодов символов, и все эти коды находятся в диапазоне от 0 до 127 (ASCII).

(equal "asdf" "ASDF")
     ⇒ nil

Функция equal рекурсивно сравнивает содержимое объектов, если они являются целыми числами, строками, маркерами, векторами, векторами bool, объектами функций байт-кода, таблицами символов, записями или объектами шрифтов. Другие объекты считаются equal только в том случае, если они eq. Например, два разных буфера никогда не считаются equal, даже если их текстовое содержимое одинаковое.

Для equal, равенство определяется рекурсивно; например, заданы два ячейки cons x и y, (equal x y) возвращает t тогда и только тогда, когда оба выражения ниже возвращают t:

(equal (car x) (car y))
(equal (cdr x) (cdr y))

Сравнение циклических списков, следовательно, может привести к глубокой рекурсии, которая приводит к ошибке, и это может привести к неинтуитивному поведению, например (equal a b) возвращает t, тогда как (equal b a) сигнализирует об ошибке.

Функция: equal-including-properties object1 object2

Эта функция ведет себя как equal во всех случаях, но также требует, чтобы две строки были равны, если они имеют одинаковые текстовые свойства.

(equal "asdf" (propertize "asdf" 'asdf t))
     ⇒ t
(equal-including-properties "asdf"
                            (propertize "asdf" 'asdf t))
     ⇒ nil

Copyright © 1990-1996, 1998-2022 Free Software Foundation, Inc.
Licensed under the GNU GPL license.
https://www.gnu.org/software/emacs/manual/html_node/elisp/Equality-Predicates.html

Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API