Nano Hash - криптовалюты, майнинг, программирование

Оператор тильда в Python

Каково использование оператора тильды в Python?

Одна вещь, о которой я могу думать, это сделать что-то с обеих сторон строки или списка, например, проверить, является ли строка палиндромной или нет:

def is_palindromic(s):
    return all(s[i] == s[~i] for i in range(len(s) / 2)) 

Любое другое хорошее использование?

29.11.2011

  • Обратите внимание, что оператор унарного дополнения ~, реализованный специальным методом __invert__, не связан с оператором not, который логически отрицает значение, возвращаемое __bool__ (или __nonzero__ в 2.x). Это также не связано с унарным оператором отрицания -, реализованным __neg__. Например, ~True == -2, что не является False или ложным, и -False == 0, которое по-прежнему является ложным. 29.11.2011
  • @eryksun, хотя то, что вы сказали, верно (-False==0). Это сбивает с толку, поскольку вы говорили о ~ и ~False == -1, что не является ложью. 06.12.2018
  • @GuilhermedeLazari, второй пример - сравнение с арифметическим отрицанием (__neg__). Вероятно, мне следовало продолжать использовать True, например. -True == -1, которое не является -2 или Falseили ложным, что более четко связывает его с результатом ~True, а также что арифметическое отрицание bool отличается от его логического отрицания. Я не пытался быть глубоким. Я просто выделил 3 операции и лежащие в их основе специальные методы, которые иногда путаются. 06.12.2018

Ответы:


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__ вашему классу. (Обратите внимание, что строки байтов [пример: '\xff'] не поддерживают этот оператор, хотя имеет смысл инвертировать все биты строки байтов.)

29.11.2011

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].

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

29.11.2011

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()]
04.09.2016
  • numpy.NaN кажется определяется как numpy.float. Если я попробую ~numpy.NaN, python жалуется, что унарный оператор ~ не определен для типа numpy.float. 14.06.2017
  • @ М.Херцкамп, это правильно. NaN, +Inf и -Inf являются особыми случаями чисел с плавающей запятой. Инвертирование битов числа с плавающей запятой привело бы к бессмысленному результату, поэтому Python этого не допускает. Вот почему вам нужно сначала вызвать .isnull() или np.isnan() для вашего массива данных, а затем инвертировать полученные логические значения. 07.11.2017
  • Обратите внимание, что ~True приводит к -2, а для логических значений numpy ~np.True_ приводит к False. 14.12.2017
  • хороший совет! Я видел, как он использовался здесь для сортировки набора данных: github.com /yu4u/age-gender-estimation/blob/master/create_db.py 13.09.2019

  • 4

    Следует отметить, что в случае индексации массива array[~i] равняется reversed_array[i]. Это можно рассматривать как индексацию, начиная с конца массива:

    [0, 1, 2, 3, 4, 5, 6, 7, 8]
        ^                 ^
        i                ~i
    
    03.02.2019
  • Это в основном потому, что значение, которое выходит из ~i (т.е. отрицательное значение), действует как отправная точка для индекса массива, который python с радостью принимает, заставляя индекс обертываться и выбирать сзади. 08.06.2019

  • 5

    Единственный раз, когда я когда-либо использовал это на практике, с numpy/pandas. Например, с помощью .isin() метода кадра данных.

    В документах они показывают этот базовый пример

    >>> df.isin([0, 2])
            num_legs  num_wings
    falcon      True       True
    dog        False       True
    

    Но что, если вместо этого вы хотите, чтобы все строки были не в [0, 2]?

    >>> ~df.isin([0, 2])
            num_legs  num_wings
    falcon     False       False
    dog        True        False
    
    08.01.2020

    6

    Я решал эту проблему с литкодом и наткнулся на этот прекрасное решение пользователя с именем Ванг Цзытао.

    Задача выглядит следующим образом: для каждого элемента в заданном массиве найти произведение всех оставшихся чисел без использования деления и за O(n) время

    Стандартное решение:

    Pass 1: For all elements compute product of all the elements to the left of it
    Pass 2: For all elements compute product of all the elements to the right of it
            and then multiplying them for the final answer 
    

    В его решении используется только один цикл for. Он вычисляет левое и правое произведение на лету, используя ~

    def productExceptSelf(self, nums):
        res = [1]*len(nums)
        lprod = 1
        rprod = 1
        for i in range(len(nums)):
            res[i] *= lprod
            lprod *= nums[i]
            res[~i] *= rprod
            rprod *= nums[~i]
        return res
    
    23.12.2019

    7

    Это второстепенное использование - тильда...

    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]
    

    приведенный выше код взят из "Практического машинного обучения"

    вы используете тильду (знак ~) в качестве альтернативы маркеру индекса знака -

    точно так же, как вы используете минус - для целочисленного индекса

    ex)

    array = [1,2,3,4,5,6]
    print(array[-1])
    

    это то же самое, что

    print(array[~1])

    13.09.2018
    Новые материалы

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

    Как написать эффективное резюме
    Предложения по дизайну и макету, чтобы представить себя профессионально Вам не позвонили на собеседование после того, как вы несколько раз подали заявку на работу своей мечты? У вас может..

    Частный метод Python: улучшение инкапсуляции и безопасности
    Введение Python — универсальный и мощный язык программирования, известный своей простотой и удобством использования. Одной из ключевых особенностей, отличающих Python от других языков, является..

    Как я автоматизирую тестирование с помощью Jest
    Шутка для победы, когда дело касается автоматизации тестирования Одной очень важной частью разработки программного обеспечения является автоматизация тестирования, поскольку она создает..

    Работа с векторными символическими архитектурами, часть 4 (искусственный интеллект)
    Hyperseed: неконтролируемое обучение с векторными символическими архитектурами (arXiv) Автор: Евгений Осипов , Сачин Кахавала , Диланта Хапутантри , Тимал Кемпития , Дасвин Де Сильва ,..

    Понимание расстояния Вассерштейна: мощная метрика в машинном обучении
    В обширной области машинного обучения часто возникает необходимость сравнивать и измерять различия между распределениями вероятностей. Традиционные метрики расстояния, такие как евклидово..

    Обеспечение масштабируемости LLM: облачный анализ с помощью AWS Fargate и Copilot
    В динамичной области искусственного интеллекта все большее распространение получают модели больших языков (LLM). Они жизненно важны для различных приложений, таких как интеллектуальные..