Constructing quines (self-reproducing functions)

前端 未结 5 1525
走了就别回头了
走了就别回头了 2021-02-19 03:47

Has anyone constructed a quine (\"A program that generates a copy of its own source text as its complete output\": http://www.nyx.net/~gthompso/quine.htm) in R? (The [quine] ta

相关标签:
5条回答
  • 2021-02-19 04:21

    This is the shortest I can come up with:

    > "f" <- function() call("<-", "f", f)
    > f()
    "f" <- function () 
    call("<-", "f", f)
    
    0 讨论(0)
  • 2021-02-19 04:28

    If you want a function that returns a function.....maybe this?

    junk <- function(...) {
      function(...) {
        structure(junk(...))
      }
    }
    

    The output is:

    > junk()
    
    function(...) {
        structure(junk(...))
      }
    <environment: 01ef8e50>
    
    
    > boo <- junk(999)
    > boo
    
    function(...) {
        structure(junk(...))
      }
    <environment: 020e1048>
    
    
    >dput(boo)
    
    function (...) 
    {
        structure(junk(...))
    }
    
    0 讨论(0)
  • 2021-02-19 04:32

    Using what body does as inspiration, call can be used to reproduce the calling command:

    f <- function () 
    {
        call("<-", as.name(as.character(sys.calls()[[1]])), sys.function(sys.parent()))
    }
    

    Which outputs:

    > f()
    f <- function () 
    {
        call("<-", as.name(as.character(sys.calls()[[1]])), sys.function(sys.parent()))
    }
    
    0 讨论(0)
  • 2021-02-19 04:40

    While I'm not sure if this "counts" from a quine perspective (I stumbled across this question while trying to verify if it does), the script

    function(){}
    

    will output function(){}. This works on the same principle as Joshua Ulrich's answer, just pared down to the essentials.

    0 讨论(0)
  • 2021-02-19 04:46

    Here is a real Quine, a program (not a function) that generates a copy of its own source text as its complete output.

    On console,

    # y1.R is a quine program
    $ cat y1.R
    (function(x){cat(x);cat('(');cat(intToUtf8(0x0022));cat(x);cat(intToUtf8(0x0022));cat(')')})("(function(x){cat(x);cat('(');cat(intToUtf8(0x0022));cat(x);cat(intToUtf8(0x0022));cat(')')})")
    
    # execute y1.R and show output
    $ /usr/bin/R --vanilla --slave < y1.R
    (function(x){cat(x);cat('(');cat(intToUtf8(0x0022));cat(x);cat(intToUtf8(0x0022));cat(')')})("(function(x){cat(x);cat('(');cat(intToUtf8(0x0022));cat(x);cat(intToUtf8(0x0022));cat(')')})")
    
    # save the output of the execution of y1
    $ /usr/bin/R --vanilla --slave < y1.R > y2.R
    
    # compare input and output -- exactly same.
    $ diff y1.R y2.R
    

    probably this is not the shortest one.

    UPDATED:

    and slightly shorter version:

    (function(x){cat(x,'(',d<-intToUtf8(0x0022),x,d,')',sep='')})("(function(x){cat(x,'(',d<-intToUtf8(0x0022),x,d,')',sep='')})")
    
    0 讨论(0)
提交回复
热议问题