实施斐波那契喹


13

奎因是一个程序运行时,其输出其来源。

在这个挑战中,您应该制作一个斐波那契奎因(Fibonacci-quine),奎因的一种变体。


什么是斐波那契喹?

Fibonacci-quine是一个程序,它通过以下规则输出对源的修改:

初始来源应为...2...。换句话说,来源应包含2。(为什么2?如果是1,没人会知道它是第一个还是第二个,甚至程序本身)

运行时,您应该输出源,但是只有特定数字(在此阶段为2)更改为斐波那契数列的下一个数字。例如,...3...。输出和输出等也一样。您最多可以支持2 ^ 32-1的整数。对于超出该限制的整数,可以选择下一个输出。

OP的笔记

我真的很想看到一个有创意的解决方案。我想不出一个单一的解决方案,因为挑战的两个重要方面,斐波那契和奎因,都不容易。那我等一下!



4
奎纳部分对此挑战并没有增加太多。正如答案所示,这只是“斐波那契数列中的下一个值”加上通用的quine构造函数。

我同意。我也希望看到一个有创意的解决方案。但是,如果您想要一个创造性的解决方案那么糟糕,那么为什么不把它变成代码挑战而不是代码挑战。获胜标准可以是某个时间间隔或某些时间后的最高票数。
定点

@FixedPoint“第二个条件”如何?有人提出了一个有创意的解决方案,我给他们赏金。
马修·卢

@FixedPoint那是一场人气竞赛
boboquack

Answers:


8

Mathematica,61个字节

ToString[#0 /. v:2 :> RuleCondition[Round[GoldenRatio v]]] & 

请注意有一个尾随空格。这是一个函数奎因,即上面的代码求值为一个未命名的函数,如果调用该函数,则该代码本身将以字符串形式返回(2更改为下一个斐波那契数字)。

上班真是太棘手了。基本思想是将函数本身(带有#0)并用下一个替换该数字/. v:2 :> nextFib[v]。但是,nextFib在此阶段不会进行评估,因此我们不会真正在源代码中得到新的数字。在搜寻了一段时间以找出如何强制立即评估之后,我在Mathematica.SE上找到了这篇很棒的文章。“标准”技术使用一个With块来强制进行评估,但是WReach的第二个答案包含使用未记录的内置方法的一个更短的替代方案,RuleCondition它也强制进行评估。

我们计算下一个斐波那契数的方法是利用以下事实:连续数的比率约为黄金比率1.618 ...,这在四舍五入之前都是准确的。因此,我们不必跟踪最后两个数字,只需执行即可Round[GoldenRatio v]。由于Mathematica的GoldenRation值是符号值,因此永远不会丢失精度,因此Round始终可以计算出准确的结果。

综上所述:

... #0 ... &

未命名的函数,其中#0指向函数对象本身。

... /. v:2 :> ...

2在函数的表达式树中找到一个(2当然这仅与自身匹配),将其调用v并替换为...

... RuleCondition[Round[GoldenRatio v]]

...下一个斐波那契数。

ToString[...]

并将结果表达式树转换为其字符串表示形式。


很高兴知道您有时必须努力工作:)
Greg Martin

黄金分割率没有符号吗?
caird coinheringaahing

@cairdcoinheringaahing没有。
Martin Ender

7

CJam,26个字节

2{0X{_@+_W$>!}go;\;"_~"}_~

在线尝试!

可能不是很理想。我们简单地迭代斐波那契数列,直到该值大于最后一个,然后在程序开始时将结果用作新值。


6
Thi ..这么早?
马修·罗





4

果冻,14字节

“×Øp+.ḞṭØv”Ṙv2

在线尝试!验证所有必需的迭代

怎么运行的

“×Øp+.ḞṭØv”Ṙv2  Main link. No arguments.

“×Øp+.ḞṭØv”     Set the left argument and return value to the string "×Øp+.ḞṭØv".
           Ṙ    Print a string representation of the return value and yield the
                unaltered return value.
            v2  Evaluate the return value as a Jelly program with left argument 2.
 ×Øp                Multiply the left argument by the golden ratio.
    +.              Add 0.5 to the resulting product.
      Ḟ             Floor; round the resulting sum down to the nearest integer.
        Øv          Yield the string "Øv".
       ṭ            Tack; append the result to the left to the result to the right.

1

迅捷,251个字节

对我来说有些冗长,但是我不知道如何缩短它:

import Foundation;var n="\"";var u="\\";var s="import Foundation;var n=%@%@%@%@;var u=%@%@%@%@;var s=%@%@%@;print(String(format:s,n,u,n,n,n,u,u,n,n,s,n,(round(%f*(1+sqrt(5))/2))))";print(String(format:s,n,u,n,n,n,u,u,n,n,s,n,(round(2*(1+sqrt(5))/2))))

取消高尔夫:

import Foundation
var n="\""
var u="\\"
var s="import Foundation;var n=%@%@%@%@;var u=%@%@%@%@;var s=%@%@%@;print(String(format:s,n,u,n,n,n,u,u,n,n,s,n,(round(%f*(1+sqrt(5))/2))))"
print(String(format:s,n,u,n,n,n,u,u,n,n,s,n,(round(2*(1+sqrt(5))/2))))

我的麻烦是尝试获取新版本的的报价s


1

切达 136字节

let b=1;for(let a=1;a<2;a=b-a){b+=a};let s='let b=1;for(let a=1;a<%i;a=b-a){b+=a};let s=%s;print s%b%@"39+s+@"39';print s%b%@"39+s+@"39

在线尝试!


1

Javascript(ES6),151个 60字节

新版本,感谢@ Leaky Nun

x=i=>console.log('x='+x+';x('+(i*(5**.5+1)/2+.5|0)+')');x(2)

旧版本 :

x=i=>{var s=Math.sqrt(5),a=1;f=n=>{return Math.ceil((((1+s)/2)**n-((1-s)/2)**n)/s)};while(f(++a)<=i);console.log('x='+String(x)+';x('+f(a)+')');};x(2)

基于


1
欢迎来到PPCG!希望您在这里过得愉快。
Leaky Nun

@LeakyNun希望现在修复!
rbntd

高尔夫球版:x=i=>console.log('x='+x+';x('+(i*(5**.5+1)/2+.5|0)+')');x(2)
Leaky Nun

@LeakyNun哇,太短了!但这不是太近似吗?对于正确的答案应为46368,i = 31000的输出为50159
rbntd

我不明白 31000不是斐波那契数。
Leaky Nun

1

dc,35个字节

2[r9k5v1+2/*.5+0k1/n91PP93P[dx]P]dx

带有迭代的版本(56字节):

2[rsP1dsN[lN+lNrsNdlP[s.q]s.=.lFx]dsFxlNn91PP93P[dx]P]dx

1

迅捷,235个字节

这是一个改进版本迦勒答案

import Foundation;var n="\"",u="\\",s="import Foundation;var n=%@%@%@%@,u=%@%@%@%@,s=%@%@%@;print(String(format:s,n,u,n,n,n,u,u,n,n,s,n,(round(%f*(1+sqrt(5))/2))))";print(String(format:s,n,u,n,n,n,u,u,n,n,s,n,(round(2*(1+sqrt(5))/2))))

0

Java(OpenJDK 8),239字节

interface a{static void main(String[]p){int a=1,b=1;for(;a<2;a=b-a)b+=a;String s="interface a{static void main(String[]p){int a=1,b=1;for(;a<%d;a=b-a)b+=a;String s=%c%s%c;System.out.printf(s,b,34,s,34);}}";System.out.printf(s,b,34,s,34);}}

在线尝试!

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.