两对多输出


17

挑战

我向您介绍了另一种间谍对抗间谍挑战,点刺混淆器与饼干。但是,在这种情况下,要保护的数据不是输入而是输出

挑战的规则很简单。编写具有以下规范的例程:

  1. 该例程可以用任何语言编写,但不能超过320个字节。
  2. 该例程必须接受三个32位带符号整数作为输入。它可以采用接受3个参数的函数,接受单个3元素数组的函数或从任何标准输入读取3个整数的完整程序的形式。
  3. 该例程必须输出一个带符号的32位整数。
  4. 在所有可能的输入中,例程必须输出2到1000(含)之间的唯一值。例程可以输出的唯一值的数量称为其

例如,C程序

int foo( int i1, int i2, int i3 ) {
    return 20 + (i1^i2^i3) %5;
}

具有9的关键,因为它(希望)只能输出的九个值1617181920212223,和24

其他一些限制如下:

  1. 该例程必须是完全确定性的并且是时不变的,对于相同的输入返回相同的输出。该例程不应调用伪随机数生成器。
  2. 该例程可能不依赖于“隐藏变量”,例如文件中的数据,系统变量或深奥的语言功能。例如,例程通常不应引用常量,除非常量在代码本身中明确定义。强烈建议不要使用依赖于编译器怪癖的例程,数学上未定义的操作的输出,算术错误等。如有疑问,请询问。
  3. 您(编码人员)必须精确知道例程可以产生多少个唯一输出,并且应该能够提供至少一个产生每个输出的输入序列。(由于可能有成百上千的唯一输出,因此只有在您的密钥被争用的情况下才需要此集合。)

由于此问题与经典加密几乎没有相似之处,因此,我希望它将为更多的读者所熟悉。

越有创意,就越好。

计分

每字节计数最短的未破解提交将被宣布为获胜者。

如果有任何混淆,请随时提出或评论。

反挑战

鼓励所有读者,包括那些已提交自己例程的读者,“破解”提交的内容。当提交的密钥发布在关联的注释部分中时,该提交将被破解。如果提交的内容持续存在72小时而不被修改或破解,则被认为是“安全的”,随后在破解方面的任何成功都将被视为比赛的原因。

每个读者每次提交只能进行一次破解尝试。例如,如果我向用户X提交:“您的密钥是20”,但我错了,用户X将拒绝我的猜测为错误,并且我将不再能够为该提交提交其他猜测。

破解的提交将被排除在争用之外(前提是它们不安全)。不应对其进行编辑。如果读者希望提交新的例程,则应在单独的答案中提交。

破解者的分数是破解者提交的内容(符合或不符合)的数量。对于计数相同的饼干,排名由所有破解提交中的总字节数决定(越高越好)。

得分最高的饼干将与获胜常规的开发者一起宣布为获胜者。

请不要破解您自己的提交。

祝你好运。:)

排行榜

上次更新时间:9月2日,美国东部标准时间上午10:45

不可逾越的壁垒(非破解提交):

  1. CJam,105 [丹尼斯]

不可阻挡的力量(爆竹):

  1. 丹尼斯[ Java,269 ; C,58Mathematica,29 ]
  2. 马丁·布特纳[ Java,245 ]

11
我可以建议[警察和强盗]作为应对这些挑战的标签吗?我认为这是此类游戏在安全性上的比较老套的名称,它可能会比[对抗性]引起更多的兴趣。
2014年

当然。我现在将其更改。
COTO

什么样的输出是可以接受的?STDOUT return等...
Ypnypn 2014年

2
您的示例不正确;其签名为9。%5可以返回-4到4之间的任何值。
基思·兰德尔

1
@丹尼斯,我可以再试一次。把它弄乱是我的错。
舒展疯子

Answers:


7

CJam,105个字节

1q~]4G#b2A#md"M-k^XM-WHM-n^GM-0%M-uwM-gM-^XeM-kM-^VO^Ph,M-^MM-^PM-qM-!M-8M-AM-OM-~tM-^FM-cM-h^AM-0M-0M-lM-@M-^[MF=M-^Z^SM-1M-KM-T2M-9M-UmSM-N
M-8M-^^M-n$4M-^M^SM-x M-OM-^@^?"256b@D#Y256#%2+md!A3#*)%)%

上面使用插入符号和M表示法,因为它包含不可打印的字符。将字节流转换为整数(256b)后,将执行以下代码:

1q~]4G#b2A#md
12313030820310059479144347891900383683119627474072658988524821209446180284434934346766561958060381533656780340359503554566598728599799248566073353154035839
@D#Y256#%2+md!A3#*)%)%

您可以在CJam解释器中在线尝试该版本。

怎么运行的

此提交使用数字理论而不是混淆。程序将为几乎所有输入返回0。从导致非零输出的少数输入中,得出秘密模数,该模数将应用于第三整数的10个最低有效位。

解决这个挑战(我能想到的)的最有效方法是分解512位整数,我希望在72小时内无法实现。

" Prepend 1 to the numbers read from STDIN and convert the resulting array into an integer
  (“N”) by considering them digits of a base 2**32 number.                                 ";

1q~]4G#

" Compute “N / 1024” and “N % 1024”.                                                       ";

2A#md

" Push a carefully selected 512 bit semi-prime (“S”).                                      ";

12313030820310059479144347891900383683119627474072658988524821209446180284434934346766561958060381533656780340359503554566598728599799248566073353154035839

" Compute P = (N / 1024) ** 13 % 2 ** 256 + 2.                                             ";

@D#Y256#%2+

" Compute “S / P” and “S % P”.                                                             ";

md

" Compute “M = (S / P) % (1000 * !(S % P) + 1) + 1”.

  “M” is the key if P is a divisor of S; otherwise, “M == 1”.                              ";

!A3#*)%)

" Compute the final output: “N % 1024 % M”.                                                ";

%

运行示例

$ base64 -d > outputs.cjam <<< MXF+XTRHI2IyQSNtZCLrGNdI7gewJfV355hl65ZPEGgsjZDxobjBz/50huPoAbCw7MCbTUY9mhOxy9QyudVtU84KuJ7uJDSNE/ggz4B/IjI1NmJARCNZMjU2IyUyK21kIUEzIyopJSkl
$ wc -c outputs.cjam
105 outputs.cjam
$ LANG=en_US cjam outputs.cjam < outputs.secret; echo
1
$ LANG=en_US cjam outputs.cjam <<< '1 2 3'; echo
0

您对加密方面的知识太了解了。;)
COTO 2014年

11
“此提交使用数字理论而不是混淆。” 看代码 “嗯,对。”
ɐɔıʇǝɥʇuʎs

4

Java的-269

感谢大家的耐心等待,现在应该解决此问题。

缩短:

int a(int a,int b,int c){double d=180-360.0/(int)(Math.abs(Math.sin(a*60))*50+2),e=180-360.0/(int)(Math.abs(Math.cos(b*60))*50+2),f=180-360.0/(int)(Math.atan2(c*60, a*60)*51+2);if(Math.abs(d+e+f-360)<.1)return Integer.valueOf((int)d+""+(int)e+""+(int)f);else return 1;}

不缩短:

int a(int a, int b, int c) {
    double d = 180 - 360.0 / (int) (Math.abs(Math.sin(a * 60)) * 50 + 2);
    double e = 180 - 360.0 / (int) (Math.abs(Math.cos(b * 60)) * 50 + 2);
    double f = 180 - 360.0 / (int) (Math.atan2(c * 60, a * 60) * 51 + 2);
    if (Math.abs(d + e + f - 360) < .1)
        return Integer.valueOf((int) d + "" + (int) e + "" + (int) f);
    else
        return 1;
}

通过更改double e,f,d=...;e=...;f=...;double d=...,e=...,f=...;
Ypnypn

@Ypnypn谢谢!添加到高尔夫版本。
拉伸狂人2014年

1
第二次尝试(得到明确许可):122
丹尼斯

1
@丹尼斯干得好!(就这样)
Stretch Maniac

1
@Dennis在那种情况下,您会忘记1并且您的答案也是不正确的;)(123是正确的……有人来抓取破解分数……)。我猜sin == 1.0当他说122正确时,Stretch Maniac并没有解释。
Martin Ender 2014年

2

采样器

当然不是官方条目,而且字符数太高,但是我认为如果有人想挑战头脑麻木的挑战,他们可以尝试确定以下函数产生了多少唯一输出(给定OP中的三个输入) :

function z(y,_,$){M=[];N=[];O=[];C=1792814437;P=72;r=t=0;(f=function(a,k,L){if(k<a.length){for(L=a[k],a[k]=0;a[k]<L;a[k]++)f(a,k+1)}else
if(!t){f([P-1,P-1],0,++t);N=M;while(t<2*P){s=!(t&1);f([P,P,P,P],0,++t);r=r||(s?0:t);t&1&&(N=O);O=[]}}else
((t<2)&&(((d=P*a[0]+(P+1)*a[1]+P)<(P<<6))&&(M[d]=(((y^~_)>>a[0])+((_^~$)>>(a[0]-32)))&1),((a[1]<P-a[0])&&
(M[a[1]+(P+1)*a[0]]=(($^C)>>a[0]+16-a[1])&1))||1))||((t&1)&&((O[P*a[2]+a[3]]|=M[a[1]+P*a[2]]&N[P*a[0]+a[3]]&&
!(a[0]-a[1]))||1))||(s|=N[(a[0]+1)*a[1]+a[3]]);})([],0,0);return r;}

实际上,我对它的坚不可摧充满信心,我将授予所有破解它的人“最高不可阻挡的自然力量奖”。

因为确实,他们应得的。


1
您应该为此悬赏!
Orby 2014年

1
@Orby很好,但是很难给评论奖励。
Geobits 2014年


@COTO这个挑战还在吗?
Soham Chowdhury 2014年

@ SohamChowdhury:绝对。如果您能弄清楚,我将在OP中阐述您的胜利。如果没有,请告诉我,我将发布解决方案。
COTO

2

C,58字节(破解)

一个简单的:

f(a,b,c){return(long long)a*b*c-0x1d21344f8479d61dLL?0:a;}

2
7(-15485867, -1299721, -104287, 0, 104287, 1299721, 15485867)。
丹尼斯2014年

那太快了:)
Orby 2014年

2

Java-245

马丁·布特纳(MartinBüttner)破解

int a(int[]_$){return $($($_(_$[0],0)))+$_(_$[1],1)*11+$($($_(_$[1+1],0)))*(1+1);}int $_(int $,int $_){int OO=0,o=1,O=1;for($=$<0?-$:$;++O*O<=$;OO+=$%O<1?O:0,o+=$%O<1?1:0,$/=$%O<1?O--:1);return $_>0?o:OO+$;}int $(int $){return(int)Math.sqrt($);}

喂输入作为int数组:a(new int[]{1,2,3})。我不希望它持续72个小时,但是会很有趣。

这是带有换行符的,以使其更具可读性:

int a(int[]_$){return $($($_(_$[0],0)))+$_(_$[1],
1)*11+$($($_(_$[1+1],0)))*(1+1);}int $_(int $,int
$_){int OO=0,o=1,O=1;for($=$<0?-$:$;++O*O<=$;OO+=
$%O<1?O:0,o+=$%O<1?1:0,$/=$%O<1?O--:1);return $_>
0?o:OO+$;}int $(int $){return(int)Math.sqrt($);}

只是蛮横... 90?
矢量化2014年

@bitpwner不,对不起。
Geobits 2014年

1
我对此进行了一些模糊化处理:pastebin.com/8pvvfFYB(我希望在替换变量名称时不要犯任何错误。)
Martin Ender 2014年

4
好的,这是我的尝试:965?
Martin Ender 2014年

1
@MartinBüttner正确。感谢混淆的版本:D
Geobits,2014年

1

Mathematica,29个字节,密钥:715,由丹尼斯破解

这只是我最初答案的固定版本,不适用于非肯定输入。

f=Plus@@Mod[NextPrime@#,240]&

接受整数列表,例如

f[{1,2,3}]

我发现了349独特的输出。范围是从3717
PhiNotPi 2014年

@PhiNotPi错误。(我仔细检查了)
Martin Ender 2014年

好吧,我发现了自己的错误和正确的答案。太晚了。
PhiNotPi 2014年

1
如果我从Mathematica文档和WolframAlpha中拼凑的东西是正确的,则密钥为715(3 ... 717)。
丹尼斯

2
Mathematica看起来是一种不错的语言,但是要么太昂贵,要么我太便宜……
丹尼斯

0

尚未混淆的C / C ++中的207个字符:

int x(int a, int b, int c) {
    int d, e, f;
    for (int i=0; i!=1<<31; ++i) {
        d=10*(b-a);
        e=a*(28-c)-b;
        f=a*b-2.7*c;
        a += d;
        b += e;
        c += f;
    }
    return ((a%5+5)*10+(b%5+5))*10+c%5+5;
}

只是想试试我的运气... 729.
矢量化

@bitpwner该死,我只是想说。:D ...如果那是错误的,那是上限。
Martin Ender 2014年

2
这不是有效的提交。循环内的所有分配都可能导致有符号整数溢出,该溢出具有未定义的行为。
丹尼斯
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.