ANSI C99 中的文本转 Brainfuck/RNA 转换器

Brainfuck 编码器

以下小型 ANSI C99 程序从 stdin 读取字符串并打印出在 stdout 上打印相同字符串的 Brainfuck 程序。

使用 gcc -o bf bf.c 编译

像这样使用:

bf_usage.sh
cat my.txt | ./bf > my.bf

源代码:

bf_encoder.c
#include <stdio.h>
#include <stdlib.h>

int main(int argc, char** argv) {
    unsigned char c;
    unsigned char curval = 0;
    //用 8 初始化 reg+1
    while(1) {
        c = getchar();
        if(feof(stdin)) {break;}
        while(curval != c) {
            if(curval < c) {
                putchar('+');
                curval++;
            } else if(curval > c) {
                putchar('-');
                curval--;
            }
        }
        putchar('.');
    }
}

它如何工作?

基本上它只使用 Brainfuck 图灵机的一个寄存器,并递增或递减寄存器以便能够打印下一个字节。它不使用 Brainfuck 中任何更"高级"的功能如循环。

Brainfuck 解码器

unbfbf 的对应解码器 - 一个简单的 brainfuck 转换器,只解释 +-. 指令。不解释其他指令。

unbf.c
#include <stdio.h>
#include <stdlib.h>

int main(int argc, char** argv) {
    char c;
    char curval = 0;
    //用 8 初始化 reg+1
    while(1) {
        c = getchar();
        if(feof(stdin)) {break;}
        if(c == '+') {
            curval++;
        } else if(c == '-') {
            curval--;
        } else if(c == '.') {
            putchar(curval);
        }
    }
}

如果你将 bf 的输出管道到 unbfunbf 的输出等于 bf 的输入,换句话说:

bf_pipe_example.sh
cat my.txt | ./bf | ./unbf

等同于

cat_mytxt.sh
cat my.txt

RNA 编码器

RNA 是一种不太知名的深奥语言,列在 esolangs.org wiki 上。也有此语言的参考实现

rna_encoder.c
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
/**
 * 这是一个文本转 RNA [0] 转换器
 * 它从 stdin 读取字节流并生成 RNA 代码
 * 当输入到 [1] 的解释器时打印从 stdin 读取的字节流。
 *
 * 参考:
 * [0]: http://esolangs.org/wiki/RNA
 * [1]: http://esolangs.org/wiki/RNA/rna.c
 */

/**
 * 返回 A、U、G 和 C 中的随机一个
 */
char randomNucleotide(void) {
    int rnd = rand() % 4;
    if(rnd == 0) {return 'A';}
    if(rnd == 1) {return 'U';}
    if(rnd == 2) {return 'G';}
    if(rnd == 3) {return 'C';}
}

//*ptr=*ptr==memory[strg]?1:0
void printGlutamicAcid() {
    if(rand() % 2 == 0) {printf("GAA");}else{printf("GAG");}
}

//strg=*ptr
void printAlanine() {
    int rnd = rand() % 4;
        if(rnd == 0) {printf("GCA");}
        if(rnd == 1) {printf("GCC");}
        if(rnd == 2) {printf("GCG");}
        if(rnd == 3) {printf("GCU");}
}

//ptr=&memory[strg]
void printThreonine() {
    int rnd = rand() % 4;
        if(rnd == 0) {printf("ACA");}
        if(rnd == 1) {printf("ACC");}
        if(rnd == 2) {printf("ACG");}
        if(rnd == 3) {printf("ACU");}
}

//*ptr+=memory[strg]
void printArginine() {
    int rnd = rand() % 6;
        if(rnd == 0) {printf("AGA");}
        if(rnd == 1) {printf("AGG");}
        if(rnd == 2) {printf("CGA");}
        if(rnd == 3) {printf("CGC");}
    if(rnd == 4) {printf("CGG");}
    if(rnd == 5) {printf("CGU");}
}

void printGlutamine() {
    int rnd = rand() % 2;
        if(rnd == 0) {printf("CAA");}
        if(rnd == 1) {printf("CAG");}

}

void printTryptophan() {
    printf("UGG");
}

void printLeucine() {
    int rnd = rand() % 4;
        if(rnd == 0) {printf("CUA");}
        if(rnd == 1) {printf("CUC");}
        if(rnd == 2) {printf("CUG");}
        if(rnd == 3) {printf("CUU");}
}

void printTerminator() {
    int rnd = rand() % 3;
        if(rnd == 0) {printf("UAA");}
        if(rnd == 1) {printf("UAG");}
        if(rnd == 2) {printf("UGA");}
}

int main(int argc, char** argv) {
    unsigned char c;
    char* codon = (char*)malloc(3*sizeof(char)); //为"基因"前后生成随机密码子
    srand(time(0));
    int codonsBefore = rand() % 1000;
    int i;
    for(i = 0; i < codonsBefore; i++) {
        //Generate random codons until one that is not AUG has been generated
        while(1) {
            codon[0] = randomNucleotide();
            codon[1] = randomNucleotide();
            codon[2] = randomNucleotide();
            if(strcmp(codon, "AUG") != 0) {
                break;
            }
        }
        printf("%s",codon);
    }
    printf("AUG"); //开始
    //做一些初始化
    printGlutamicAcid(); //将 mem[0] 设置为 1
    printAlanine(); //将 strg 设置为 1
    printThreonine(); //将 ptr 设置为 strg == 1
    printGlutamicAcid(); //将 mem[1] 设置为 1
    printTryptophan(); //将 strg 设置为 0(ptr 仍为 1)
    unsigned char curval = 1;
    while(1) {
        c = getchar();
        if(feof(stdin)) {break;}
        //将 *ptr 重新初始化为 1
        while(curval != c) {
            if(curval < c) {
                printArginine();
                curval++;
            } else if(curval > c) {
                printGlutamine();
                curval--;
            }
        }
        printLeucine();
    }
    printTerminator();
    //在终止子之后打印随机密码子
    int codonsAfter = rand() % 1000;
        for(i = 0; i < codonsBefore; i++) {
                while(1) {
            codon[0] = randomNucleotide();
            codon[1] = randomNucleotide();
            codon[2] = randomNucleotide();
            //来自的 RNA 解释器
            if(strcmp(codon, "AUG") != 0) {
                break;
            }
        }
                printf("%s",codon);
        }

    //释放为生成随机密码子占用的内存
    free(codon);
}

它如何工作

与文本转 Brainfuck 转换器不同,此转换器不是确定性工作,而是每次调用产生不同结果。

几个因素导致此情况:

你有没有考虑过将你的宝贵数据隐藏在其他 ORF 中 ;-?


Check out similar posts by category: C/C++, Fun