2016-02-05 61 views
1

我需要在密码查询中按位“和”。似乎cypher不支持按位操作。任何建议的替代品? 这就是我想要检测的... 例如,268是(2^8 + 2^3 + 2^2),正如你所看到的,2^3 = 8是我原始数字的一部分。所以,如果我使用按位与(100001100)&(1000)= 1000,那么我可以检测8是否是268的一部分。 如何在没有按位支持的情况下执行此操作?有什么建议么?我需要在密码中这样做。Neo4j密码查询中的按位操作替代

回答

0

谢谢戴夫。我试过你的解决方案,他们都工作。对我来说,找到另一种方法是一个很好的暗示。这是我解决它的方式。我用字符串比较。

with '100001100' as number , '100000000' as sub_number 
with number,sub_number,range(length (number)-1,length (number)-length(sub_number),-1) as tail,length (number)-length(sub_number) as difference 
unwind tail as i 
with i,sub_number,number, i - length (number) + length (sub_number) as sub_number_position 
with sub_number_position, (split(number,''))[i-1] as bit_mask , (split(sub_number,''))[sub_number_position] as sub_bit 
with collect(toInt(bit_mask) * toInt(sub_bit)) as result 

return result 

显然,数字和子编号可以有不同的值。

0

几乎可以肯定失败选择在第一时间按位操作的目的,但如果你绝对需要两个二进制数的暗号,你可以做这样的事情与收藏。

with split('100001100', '') as bin_term_1 
, split('000001000', '') as bin_term_2 
, toString(1) as one 
with bin_term_1, bin_term_2, one, range(0,size(bin_term_1)-1,1) as index 
unwind index as i 
with i, bin_term_1, bin_term_2, one, 
case 
    when (bin_term_1[i] = one) and (bin_term_2[i] = one) then 
    1 
    else 
    0 
    end as r 
return collect(r) as AND 
1

如果你绝对必须做暗号的操作可能是一个更好的解决办法是实现像@埃文的SO解决方案Alternative to bitwise operation使用暗号。

您可以通过使用暗号,看起来像这样将您的数据开始...

// convert binary to a product of prime numbers 
// start with the number to conver an a collection of primes 
with '100001100' as number 
, [2,3,5,7,13,17,19,23,29,31,37] as primes 

// create an index based on the size of the binary number to convert 
// take a slice of the prime array that is the size of the number to convert 
with number 
, range(length(number)-1,0,-1) as index 
, primes[0..length(number)] as primes, decimals[0..length(number)] as decimals 

// iterate over the index and match the prime number to the bits in the number to convert 
unwind index as i 
with (split(number,''))[i] as binary_place_holder, primes[-i-1] as prime_place_holder, decimals[-i-1] as decimal_place_holder 

// collect the primes that are set by multiplying by the set bits 
with collect(toInt(binary_place_holder) * prime_place_holder) as prime_placeholders 

// filter out the zero bits 
with filter(p in prime_placeholders where p > 0) as prime_placeholders 

// return a product of primes of the set bits 
return prime_placeholders, reduce(pp = 1, p in prime_placeholders | pp * p) as prime_product 

样品上面查询的输出。该查询可以适用于使用主要产品更新属性。

enter image description here

这里是当你想使用它,你可以使用素数的模量的位置转换如何分解

enter image description here

然后屏幕帽你想测试的位。

// test if the fourth bit is set in the decimal 268 
// 268 is the equivalent of a prime product of 1015 
// a modulus 7 == 0 will indicate the bit is set 
with 1015 as prime_product 
, [2,3,5,7,13,17,19,23,29,31,37] as primes 
, 4 as bit_to_test 
with bit_to_test 
, prime_product 
, primes[bit_to_test-1] as prime 
, prime_product % primes[bit_to_test-1] as mod_remains 
with 
    case when mod_remains = 0 then 
    'bit ' + toString(bit_to_test) + ' set' 
    else 
    'bit ' + toString(bit_to_test) + ' NOT set' 
    end as bit_set 
return bit_set 
2

使用密码执行此类型测试的另一种方法是将您的十进制值转换为表示已设置位的小数的集合。

// convert the binary number to a collection of decimal parts 
// create an index the size of the number to convert 
// create a collection of decimals that correspond to the bit locations 
with '100001100' as number 
, [1,2,4,8,16,32,64,128,256,512,1024,2048,4096] as decimals 
with number 
, range(length(number)-1,0,-1) as index 
, decimals[0..length(number)] as decimals 

// map the bits to decimal equivalents 
unwind index as i 
with number, i, (split(number,''))[i] as binary_placeholder, decimals[-i-1] as decimal_placeholder 

// multiply the decimal value by the bits that are set 
with collect(decimal_placeholder * toInt(binary_placeholder)) as decimal_placeholders 

// filter out the zero values from the collection 
with filter(d in decimal_placeholders where d > 0) as decimal_placeholders 
return decimal_placeholders 

下面是返回结果的示例。

enter image description here

然后,当你要测试的号码是否是小数,你可以测试实际小数集合中存在。

with [4, 8, 256] as decimal_placeholders 
, 8 as decimal_to_test 
return 
    case 
    when decimal_to_test in decimal_placeholders then 
     toString(decimal_to_test) + ' value bit is set' 
    else 
     toString(decimal_to_test) + ' value bit is NOT set' 
    end as bit_set_test 
0

或者,如果有一个APOC可用,他们可以使用apoc.bitwise.op这是一个围绕java按位操作的包装。

RETURN apoc.bitwise.op(268, "&",8) AS `268_AND_8` 

其产生以下结果

enter image description here