原始字符串


27

Primenary(binary-prime)字符串是这样的字符串,当以二进制网格形式编写时,每一行和每一列都有一个素数总计。

这是一个模糊的解释,所以让我们用一个可行的例子来分解它。


在此示例中,我们将使用字符串bunny

首先,找到每个字符的ASCII码点及其二进制表示形式:

Char | ASCII | Binary

b      98      1100010
u      117     1110101
n      110     1101110
n      110     1101110
y      121     1111001

从上到下取这些二进制值,并将它们排列到网格中(如有必要,添加前导零):

1 1 0 0 0 1 0
1 1 1 0 1 0 1
1 1 0 1 1 1 0
1 1 0 1 1 1 0
1 1 1 1 0 0 1

然后,计算1每一行和每一列中s 的数量:

1 1 0 0 0 1 0   > 3
1 1 1 0 1 0 1   > 5
1 1 0 1 1 1 0   > 5
1 1 0 1 1 1 0   > 5
1 1 1 1 0 0 1   > 5

v v v v v v v

5 5 2 3 3 3 2

当且仅当每一个总数都是质数(例如此处)时,字符串才是有效的二进制质数。


挑战

您的任务是创建一个函数或程序,当给定一个字符串时,truthy如果该字符串是素数则返回/输出,falsy否则返回。

规则/细节

  • 您可以假定字符串的字符将始终在ASCII范围内33-126(包括ASCII )。
  • 该字符串将不会为空。
  • 一个primenary串并没有必须有一个最佳长度-例如,W1n*是有效的,尽管有4个字符。
  • 这是,因此最短的答案(以字节为单位)获胜-但欢迎所有提交。
  • 禁止出现标准漏洞。

测试用例

'husband'     -> True
'HOTJava'     -> True
'COmPaTIBILE' -> True
'AuT0HACk'    -> True

'PPCW'        -> False
'code-golf'   -> False
'C++'         -> False
'/kD'         -> False

'HI'          -> False
'A'           -> False

在repl.it上还有一个有效但冗长的Python示例,您可以据此测试解决方案。


请问您husband是怎么发现的呢?还是其中任何一个?不过,这是个大问题!
加布里埃尔·贝纳米

3
@GabrielBenamy我很高兴有人问!我浏览了一个在线词典文件,尝试将每个字母随机大写,有时将字母换成数字,等等。然后,我浏览了输出列表并选择了一些我喜欢的测试用例
FlipTack

每个1-2个字符的输入保证返回False,对吗?
mbomb007 '16

...因为01不是素数,所以每个仅包含给定范围内char的1-2 char输入字符串保证至少包含一个01作为垂直和。您应该添加一些1和2字符串作为测试用例。
mbomb007 '16

@ mbomb007 1个char输入不能按列有质数,因此它们将返回false。2个字符输入可以但不在我们使用的ASCII范围内,因此对于这种情况,您是正确的。
FlipTack

Answers:


8

MATL,10个字节

BtXsw!shZp

在线尝试!

这是工作的理想语言。这几乎就是挑战说明的字面意思。

Bt % Converts input to binary matrix, duplicate
Xs  % Sum columns (alternative X version to prevent defaulting to sum along first non-singleton dimension, thanks @Jonathan Allan)
w! % Get the duplicate to the top of the stack, transpose
s  % Sum again
h  % Concatenate horizontally
Zp % Check primality element-wise. Display implicitly.

由于任何零都会使每个元数据的MATL数组为假,因此不需要其他任何东西-基本上,A?(if)上调用了隐式。


a应该是虚假的,但是会返回1 1?(其列的
总和

我认为BtXsw!shZp可以解决这个问题,并为10赢家
乔纳森·艾伦

@ Flp.Tck使用行向量时完全忘记了MATLAB的“宽恕”行为。对不起,现在修复。
桑契斯,2016年

现在可以正常工作:)(可能想更新在线尝试链接tho)
FlipTack

@ Flp.Tkc完成。感谢您的挑战!
桑契斯

4

果冻13 12 11 字节

OBUZ;$S€ÆPẠ

TryItOnline!所有测试用例

怎么样?

OBUZ;$S€ÆPẠ - Main link: word                  e.g. ha!
O           - cast to ordinals                 e.g. [104,97,33]
 B          - convert to binary                e.g. [[1,1,0,1,0,0,0],[1,1,0,0,0,0,1],[1,0,0,0,0,1]]
  U         - reverse each entry (say "b")     e.g. [[0,0,0,1,0,1,1],[1,0,0,0,0,1,1],[1,0,0,0,0,1]]
     $      - last two links as a monad
   Z        - transpose                        e.g. [[0,1,1],[0,0,0],[0,0,0],[1,0,0],[0,0,0],[1,1,1],[1,1]]
    ;       - concatenate with "b"             e.g. [[0,1,1],[0,0,0],[0,0,0],[1,0,0],[0,0,0],[1,1,1],[1,1],[0,0,0,1,0,1,1],[1,0,0,0,0,1,1],[1,0,0,0,0,1]]
      S€    - sum €ach                         e.g. [2,0,0,1,0,3,2,3,3,2]
        ÆP  - is prime (1 if prime, 0 if not)  e.g. [1,0,0,0,0,1,1,1,1,1]
          Ạ - all truthy?                      e.g. 0


3

果冻,15字节

O+⁹Bṫ€3µS€;SÆPP

在线尝试!验证所有测试用例。

说明

O+⁹Bṫ€3µS€;SÆPP  Main link. Input: string z
O                Ordinal, get ASCII value of each char
  ⁹              Nilad representing 256
 +               Add 256 to each ordinal value
   B             Binary digits of each
    ṫ€3          Tail, take each list of digits from the 3rd value to the end
                 These are the last seven digits of each
       µ         Start a new monadic chain
        S€       Sum each list of digits by rows
           S     Sum by column
          ;      Concatenate
            ÆP   Test if each is prime, 1 if true else 0
              P  Product

3

Mathematica,75个字节

And@@Join@@PrimeQ@{+##&@@#,+##&@@@#}&@IntegerDigits[ToCharacterCode@#,2,7]&

未命名函数,将字符串作为输入并返回TrueFalse

ToCharacterCode@#将输入转换为其ASCII值列表;IntegerDigits[...,2,7]将每个值放入其位列表,如有必要,将其填充为长度7。所以现在我们有了一个2D数组,我们想要它的所有行总和和列总和。瞧,字符痉挛{+##&@@#,+##&@@@#}&@...确实做到了这一点(它使用+##&,将“所有参数加总”,使用函数在第一个坐标中的向量列表中使用@@,并将每个函数作为其在第二坐标中的整数列表使用@@@) 。然后,我们只检查结果是否为PrimeQ,使用展平列表Join@@,然后取And所有这些值中的。


2

红宝石 -rprime,100字节

->s{a=s.bytes.map{|b|b.digits 2}
a.all?{|r|r.sum.prime?}&([0]*7).zip(*a).all?{|c|c.count(1).prime?}}

在线尝试!

说明

->s{
    a=s.bytes                       # Get byte values from string
             .map{|b|b.digits 2}    # For each, map it to its binary digits
                                    #   (least significant digits first)
a.all?{|r|r.sum.prime?}             # Each character has a prime number of 1's?
    &                               # Bit-and (because it saves bytes here)
    ([0]*7).zip(*a)                 # Zip bit array with an all-zero array
                                    #   (If we don't, then uneven array lengths
                                    #   cause some columns to not be returned.)
    .all?{|c|c.count(1).prime?}     # All columns have a prime number of 1's?
                                    #   (We use count instead of sum here because
                                    #   zip pads columns with trailing nils, which
                                    #   can't be added to numbers via sum.)
}

1

Perl中,151 121 111 + 3 = 114个字节

与运行 -lF。该程序将仅对第一个输入正确运行。终止程序,然后重新运行以进行下一个输入。

感谢@Dada让我知道//以后的事F是多余的。可以通过在via中管道输入来删除一个额外的字节(对于112)echo -n,但是我觉得这在技术上增加了更多的代码,所以YMMV。

for$c(@a=map{sprintf"%07b",ord}@F){$b[$_].=substr$c,$_,1 for 0..6}s/0//g,$d|=/^1?$|^(11+?)\1+$/ for@a,@b;say!$d

可读性:

                                     #Implicitly split input into characters in @F array
for$c(@a=map{sprintf"%07b",ord}@F)  #Convert @F to 7-bit binary as @a, then loop through it                        
    $b[$_].=substr$c,$_,1 for 0..6   #Transpose @a's bits into @b
}
s/0//g,$d|=/^1?$|^(11+?)\1+$/ for@a,@b; #Remove any zeros, then run through composite regex
say!$d                          #If all composite regex checks fail, then it's fully prime.

1
一个仅可用于第一个输入的版本非常好,因此您可以将141字节的版本作为主要版本,并建议另一个版本用于多个输入。
达达

另请注意,您可以省略//after -F,并且可以在不带最终换行符(带有echo -n)的情况下接受输入以摆脱-l标记。
达达

1

Python 3, 228 227 225字节

这不是一个很好的答案,我无法按照自己的意愿打高尔夫球,但是我花了很长时间才觉得应该发布它。关于削减字节的建议将不胜感激。

r=range
n=[format(ord(c),"08b")for c in input()]
n=map(lambda s:s.count("1"),n+["".join([f[1]for f in filter(lambda e:e[0]%8<1,enumerate("X"*-~i+"".join(n)))][1:])for i in r(8)])
print(all(all(s%d for d in r(2,s))for s in n))

编辑1:替换e[0]%8==0e[0]%8<1,丢失了一个字节。感谢Flp.Tkc!

编辑2:用-〜i替换(i + 1),丢失另外两个字节。感谢Erik公开了我的位知识的严重程度:)测试此修订版时,我发现它kappa是有效的……充分利用了您的需求。


1
你可以改变e[0]%8==0e[0]%8<1
FlipTack

@ Flp.Tkc好地方!没有理由不能做到这一点。
FourOhFour 2016年

1
@ Flp.Tkc我认为我不能通过使其成为函数来节省字节。我喜欢你的404 rep btw :)
FourOhFour 2016年

应该是<1,不是<0吗?
破坏的柠檬

@可破坏西瓜是的,让我纠正了这一点。
FourOhFour 2016年

1

Groovy中,151个 137字节

{p={x->x<3||(2..(x**0.5)).every{x%it}};y={it.every{p(it.count("1"))}};x=it.collect{0.toString((int)it,2) as List};y(x)&&y(x.transpose())}

groovy中没有素性检查...

p={x->x<3||(2..(x**0.5)).every{x%it}}; -封闭性测试。

y={it.every{p(it.count("1"))}}; -闭合以确保传递的二进制2D数组的所有“ 1”计数均为质数。

x=it.collect{0.toString((int)it,2) as List}; -从字符串到二进制数组的转换。

y(x)&&y(x.transpose()) -对于主矩阵和转置矩阵中所有素数验证的和,请确保它们返回true。


1

Pyth,37个字节

L.AmP_sdb=sMM.[L\0lh.MlZQ=.BMQ&yZy.TZ

在线尝试!


                                 Code | Explanation
--------------------------------------+----------------------------------------------------------------
L.AmP_sdb=sMM.[L\0lh.MlZQ=.BMQ&yZy.TZ | Full code
L                                     | Define function y(b):
   m    b                             |   For each d in b:
    P_sd                              |     Is the sum of the elements of the list prime?
 .A                                   |   Return whether all elements of the resulting list are truthy
                         =   Q        | Assign the following to Q:
                          .BMQ        |   The list of binary strings for each character in the input
         =             Z              | Assign the following to Z:
               L             Q        |   For every element in Q:
             .[ \0                    |     Pad with 0 on the left
                  lh.MlZQ             |     To the length of the longest element in Q
            M                         |   For each element in the resulting list:
          sM                          |     Convert each character to an integer
                              &yZ     | Print y(Z) AND
                                 y.TZ |   y( <Transpose of Z> )

1

Brachylog,14个字节

ạḃᵐB↔ᵐz₁,B+ᵐṗᵐ

在线尝试!

通过成功或失败输出。(在成功的情况下,可通过输出变量获得所有列和行总和的列表。

   B              The variable B is
ạ                 the codepoints of the input
 ḃᵐ               converted to lists of binary digits,
    ↔ᵐ            which with each list reversed
      z₁          then zipped without cycling
        ,B        and concatenated with B
          +ᵐ      has elements which all sum to
            ṗᵐ    prime numbers.

1

O5AB1E,12个字节

Çžy+bø€SOp¦W

在线尝试!

这是我的第一个代码高尔夫,所以轻松点:)

Ç              % Converts the implicit input into ascii values
 žy+           % Adds 128 to each value, inspired by Emigna as a way to pad zeros
    b          % Convert all values into bits
     ø         % Transpose
      €SO      % Sum each string of binary digits created
         p¦    % Check if each element is prime and cut the first element out (adding 128 makes it equal to the number of characters)
           W   % Take the minimum value to effectively "and" all the elements

对于单个字母输入,这将产生空结果。我不太熟悉O5AB1E,但是如果这是一个错误的值,那就可以了。
桑契斯

1

Python 3中209个 189 180 171 160字节

Thanx鱿鱼为-9个字节:)

def p(s):n=s.count('1');return(n>1)*all(n%i for i in range(2,n))
def f(s):t=[f'{ord(c):07b}'for c in s];return all(map(p,t+[[u[j]for u in t]for j in range(7)]))

在线尝试!


我喜欢您重写测试用例打印语句的方式:)
movatica

是的,我是对f字符串的痴迷强迫症...而且,如果您t+在map语句中删除,它是否等效?
恢复莫妮卡

不,因为素数检查需要覆盖位矩阵中的行和列。t具有所有行,[[t[i][j]..i..]..j..]而已转置t,即列。如果有一种更短的方式来转置矩阵,我们可以节省更多的字节:)
movatica

当我尝试它时它可以正常工作,您知道一个打破它的字符串吗?
恢复莫妮卡

是。 beezz应该返回false,但不会返回。这是因为素数校验被破坏,它返回True4位。尝试print(p('1111'))。立即修复。所有的测试用例都没有涵盖这一点,因为所有使用的字符都是原始字符。
movatica

1

K(OK) 40 33字节

解:

&/{2=+/d=_d:x%!x}'+/'m,+m:(7#2)\'

在线尝试!

说明:

一半是创建矩阵,另一半是素数检查。

&/{2=+/d=_d:x%!x}'+/'m,+m:(7#2)\' / the solution
                                ' / apply to each (')
                               \  / decode
                          (   )   / do this together
                           7#2    / 7#2 => 2 2 2 2 2 2 2
                        m:        / save as m
                       +          / transpose
                     m,           / append to m
                  +/'             / sum (+/) each (')
                 '                / apply to each
  {             }                 / lambda taking implicit x
              !x                  / range 0..x
            x%                    / x divided by ...
          d:                      / save as d
         _                        / floor
       d=                         / equal to d?
     +/                           / sum (+/)
   2=                             / equal to 2?
&/                                / minimum

0

PHP,173字节

for($r=1;$b=substr_count($t[$i]=sprintf('%07b',ord($argv[1][$i++])),1);)$r&=$b==2|$b%2&$b>2;for(;$k++<7;){for($b=$j=0;$t[++$j];$b+=$t[$j][$k-1]);$r&=$b==2|$b%2&$b>2;}echo$r;

在线测试


0

JavaScript,234个字节

f=z=>(z=[...z].map(v=>v.charCodeAt(0))).map(v=>v.toString(2).replace(/0/g,"").length).every((p=v=>{for(i=2;i<v;i++){if(v%i===0){return 0}};return v>1}))&&[...""+1e6].map((v,i)=>z.reduce((a,e)=>!!(e&Math.pow(2,i))+a,0)).every(v=>p(v))

通过将数字转换为二进制,使用字符串替换除去零,然后计算1,可以得到水平值。垂直和是通过循环1到7并使用按位与(AND)和2乘以n次幂而获得的。


Math.pow(2,i)可以简化为(1<<i)假设i<32,也许节省7个字节,也许不是。
鸣子

0

Clojure,180字节

#(let[S(for[i %](for[j[1 2 4 8 16 32 64]](min(bit-and(int i)j)1)))A apply](not-any?(fn[i](or(= i 1)(seq(for[d(range 2 i):when(=(mod i d)0)]d))))(into(for[s S](A + s))(A map + S))))

生成位列表和素数测试的方法可能更短。



0

Python 3,164字节

import numpy;a=numpy.array([list(f'{ord(_):07b}')for _ in input()]).astype(int);print(all([(v>1)*all(v%i for i in range(2,v))for v in set(a.sum(0))|set(a.sum(1))]))

0

Ruby 2.7,95 -rprime字节

->s{a=s.bytes.map{[*@1.digits(2),0][..6]}
(a.map(&:sum)+a.transpose.map(&:sum)).all?(&:prime?)}

没有TiO链接,因为TiO仍然运行Ruby 2.5.5。😭

说明

很简单 第一行将每个字符的二进制数字填充为一个填充为七个数字的数组,这实际上应该更容易一些:

a = s.bytes.map { [*@1.digits(2), 0][..6] }

检查出编号的块参数(@1)和beginless范围(..6辣味

第二行汇总行和列,并测试它们是否都是素数:

(a.map(&:sum) + a.transpose.map(&:sum)).all?(&:prime?)

0

的JavaScript(Node.js的)149 146 ... 134个 130 129字节

x=>[...x].map(y=>a=[...a.map(n=>y.charCodeAt()&2**i++?++z&&-~n:n,z=i=0),z],a=[...Array(7)])&&!a.some(n=>(P=r=>n%--r?P(r):~-r)(n))

在线尝试!

说明

x=>                        // Main function:
 [...x].map(               //  For each y in x:
  y=>
   a=[...a.map(            //   For each i in range(0, len(a)):
    n=>                   
     y.charCodeAt()&2**i++ //    If y AND 2**i is not zero:
     ?++z&&-~n:n,          //     z = z + 1; a[i] = a[i] + 1 (1 if a[i] is undefined)
    z=i=0                  //   Initially z = 0
   ),z],                   //   Then push z at the end of a
  a=[...Array(7)]          //  Initially a = [undefined] * 7
 )&&!a.some(               //  Then for each n in a:
  n=>(
   P=r=>                   //   Composite function:
    n%--r?                 //    If n % (r - 1) == 0 or r == 1:
     P(r)                  //     Return P(r - 1)
    :~-r                   //    Else: Return r - 2
  )(n)                     //   Starting from r = n
 )                         //  Return whether the composite function returns 0 for all n.

它甚至如何工作!

  • y.charCodeAt()&2**i
    • 我们需要此代码以返回y.charCodeAt()if 的相应位0 <= i < 7否则 0。
    • 什么时候 i < 7,代码显然可以照常工作。
    • 当时7 <= i <= 32,由于y.charCodeAt()始终为0,因此结果为预期的0。
    • 32 < i < 1024,因为int32(2**i) == 0,结果为预期的0。
    • 当时1024 <= i,我们有2**i == Infinity,并且因为int32(Infinity) == 0,结果为0预期。
  • (P=r=>n%--r?P(r):~-r)(n)
    • 为简单起见,我们让R = --r = r - 1
    • n % R == 0或时,此辅助函数终止n % R is NaN
      • n % R == 0R是的一个因素n
        • 如果是R == 1,那n是首要的,因为所有人1 < R < n不能分开n。返回0(错误)。
        • 如果R == -1是的话n == 0。返回-2(真实)。
        • 否则,返回R - 1那里R - 1 > 0(truthy)。
      • n % R is NaN:无效的模块化计算。
        • 如果R == 0n == 1。返回-1(真)。
        • 如果n is NaNR is NaN。返回-1(真)。
    • 结果,R == 1该函数仅在何时才能返回假值(表示n素数)。
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.