Побитовые операции с bigz в gmp

Я перевожу некоторые скрипты криптографии с Python на R. Похоже, что Python обрабатывает очень большие целые числа намного лучше, чем R может изначально:

10593080468914978578954316149578855170502344604886137564370015851276669104055 >> 1
# 5296540234457489289477158074789427585251172302443068782185007925638334552027

Но я знаю библиотеку gmp для R, которая хорошо с ними справляется (в основном):

as.bigz("10593080468914978578954316149578855170502344604886137564370015851276669104055")

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

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

  • Выполните эквивалент bitwAnd и bitwOr
  • По bigz значениям
  • БЕЗ потери точности.

Любые идеи?

Бонус: если вы можете дать интерпретацию bitwAnd и bitwOr в терминах базы 10, тогда это может сработать. Желательно с некоторым примером кода в R, если нет, я могу обойти это.


person Oliver Frost    schedule 28.04.2018    source источник


Ответы (1)


Я уверен, что должен быть более гладкий и быстрый способ, но один из вариантов будет примерно таким...

library(gmp)

z <- as.bigz("10593080468914978578954316149578855170502344604886137564370015851276669104055")  
w <- as.bigz("1234874454654321549879876546351546654456432132321654987584654321321")

#express as numeric vectors of 0s and 1s
z1 <- as.numeric(charToRaw(as.character(z, b=2)))-48
w1 <- as.numeric(charToRaw(as.character(w, b=2)))-48

#normalise the lengths
mx <- max(length(z1), length(w1))
z1 <- c(rep(0, mx-length(z1)), z1)
w1 <- c(rep(0, mx-length(w1)), w1)

#then do & or | and convert back to bigz
zandw <- as.bigz(paste0("0b", rawToChar(as.raw(1*(z1 & w1) + 48))))
zorw <- as.bigz(paste0("0b", rawToChar(as.raw(1*(z1 | w1) + 48))))

zandw
Big Integer ('bigz') :
[1] 905773543034890641004226585015137324621885921615658881499355162273

zorw
Big Integer ('bigz') :
[1] 10593080469244079490573747058454505131838753934720683775076011957361968263103
person Andrew Gustar    schedule 28.04.2018
comment
Сейчас меня не волнует производительность, она соответствует результатам, возвращаемым Python, так что я в восторге. Ты сделал мой день! - person Oliver Frost; 28.04.2018