Оператор тильды в Python
Какое использование оператора тильды в Python?
Одна вещь, о которой я могу думать, - это сделать что-то в обеих сторонах строки или списка, например, проверить, является ли строка палиндромной или нет:
def is_palindromic(s):
return all(s[i] == s[~i] for i in range(len(s) / 2))
Любое другое хорошее использование?
Ответы
Ответ 1
Это унарный оператор (принимающий один аргумент), который заимствован из C, где все типы данных - это просто разные способы интерпретации байтов. Это операция "инвертировать" или "дополнение", в которой все биты входных данных меняются на противоположные.
В Python для целых чисел биты двухкомпонентного представления целого числа обращаются вспять (как в b <- b XOR 1
для каждого отдельного бит), и результат интерпретируется снова как целое число с двумя дополнениями. Итак, для целых чисел ~x
эквивалентно (-x) - 1
.
Обоснованная форма оператора ~
предоставляется как operator.invert
. Чтобы поддерживать этот оператор в своем классе, дайте ему метод __invert__(self)
.
>>> import operator
>>> class Foo:
... def __invert__(self):
... print 'invert'
...
>>> x = Foo()
>>> operator.invert(x)
invert
>>> ~x
invert
Любой класс, в котором имеет смысл иметь "дополнение" или "обратное" экземпляра, который также является экземпляром одного и того же класса, является возможным кандидатом для инвертирующего оператора. Однако перегрузка оператора может привести к путанице при неправильном использовании, поэтому убедитесь, что это действительно имеет смысл сделать, прежде чем предоставлять метод __invert__
для вашего класса. (Обратите внимание, что байт-строки [ex: '\xff'
] не поддерживают этот оператор, хотя имеет смысл инвертировать все биты байтовой строки.)
Ответ 2
~
- это оператор побитового дополнения в python, который по существу вычисляет -x - 1
Итак, таблица будет выглядеть как
i ~i
0 -1
1 -2
2 -3
3 -4
4 -5
5 -6
Итак, для i = 0
он сравнивал бы s[0]
с s[len(s) - 1]
, для i = 1
, s[1]
с s[len(s) - 2]
.
Что касается вашего другого вопроса, это может быть полезно для диапазона побитовых хаков.
Ответ 3
Кроме того, что он является побитовым оператором дополнения, ~
также может возвращать логическое значение, хотя здесь нет обычного типа bool
, скорее, вы должны использовать numpy.bool_
.
Это объясняется в
import numpy as np
assert ~np.True_ == np.False_
Иногда может быть полезно обратное логическое значение, например, ниже ~
используется оператор, чтобы очистить ваш набор данных и вернуть вам столбец без NaN.
from numpy import NaN
import pandas as pd
matrix = pd.DataFrame([1,2,3,4,NaN], columns=['Number'], dtype='float64')
# Remove NaN in column 'Number'
matrix['Number'][~matrix['Number'].isnull()]
Ответ 4
Следует отметить, что в случае индексации array[~i]
равняется reversed_array[i]
. Это можно рассматривать как индексирование, начиная с конца массива:
[0, 1, 2, 3, 4, 5, 6, 7, 8]
^ ^
i ~i
Ответ 5
Это незначительное использование это тильда...
def split_train_test_by_id(data, test_ratio, id_column):
ids = data[id_column]
in_test_set = ids.apply(lambda id_: test_set_check(id_, test_ratio))
return data.loc[~in_test_set], data.loc[in_test_set]
вышеприведенный код взят из "Hands On Machine Learning"
Вы используете тильду (~ знак) в качестве альтернативы - подписать маркер индекса
так же, как вы используете минус - для целочисленного индекса
ех)
array = [1,2,3,4,5,6]
print(array[-1])
это то же самое, что
print(array[~1])