โปรแกรมที่เข้ารหัสข้อความเป็นข้อความของตัวเอง


13

เขียนโปรแกรมที่เข้ารหัสข้อความที่กำหนดให้เป็นข้อความของตัวเองโดยจัดทำเป็นอินพุตโดยไม่รบกวนตรรกะของมัน โปรแกรมจะต้องทำงานเป็นตัวถอดรหัสโดยเรียกคืนข้อความต้นฉบับจากข้อความ มันจะต้องรักษาฟังก์ชั่นการเข้ารหัส / ถอดรหัสหลังจากการแปลง

พูดอย่างเป็นทางการมากขึ้นโปรแกรมที่ต้องการ P จะต้องทำการแปลงต่อไปนี้ด้วยข้อความตัวอักษร M:
P (M, P) -> P *
P * (P *) -> M

นี่P *เป็นโปรแกรมที่ถูกแปลงซึ่งจะต้องปฏิบัติตามกฎข้างต้นนั่นคือ:
P * (M2, P *) -> P **
P ** (P **) -> M2
และอื่น ๆ ... แต่ละรายการ การเข้ารหัสที่ตามมาไม่ได้ลบข้อความที่เข้ารหัสก่อนหน้านี้ดังนั้น P ** จะมีสองข้อความ - M และ M2

วิธีที่ง่ายที่สุดสำหรับโปรแกรมที่จะแยกแยะระหว่างโหมดการเข้ารหัส / ถอดรหัสคือการมีอาร์กิวเมนต์พิเศษ M แต่การตัดสินใจขั้นสุดท้ายขึ้นอยู่กับคุณหากมีการระบุไว้อย่างชัดเจน โปรแกรมอาจอ่านข้อความของตัวเองจากไฟล์ หากภาษาที่เลือกไม่มีวิธีการนี้ข้อความต้นฉบับสามารถส่งผ่านไปยังโปรแกรมด้วยวิธีอื่นใดก็ได้

แน่นอนว่ามีวิธีแก้ปัญหาเล็กน้อยดังนั้นนี่จึงเป็นการประกวดความนิยม อย่างไรก็ตามฉันมีข้อ จำกัด สำหรับการแสดงความคิดเห็นในข้อความของโปรแกรม


ถ้าฉันเรียกโปรแกรมที่แปลงแล้ว P * ด้วยข้อความใหม่ P ** จะมีทั้งข้อความหรือเฉพาะอันสุดท้ายหรือไม่?
Tal

ดังนั้นฉันจึงได้รับรหัสโปรแกรมเป็นอินพุตเมื่อเข้ารหัสและถอดรหัส?
Martin Ender

โปรแกรมมีวัตถุประสงค์เพื่อแยกความแตกต่างระหว่างการถูกขอให้ถอดรหัสข้อความที่เข้ารหัสอย่างไรและถูกขอให้เข้ารหัสข้อความที่เพิ่งเกิดขึ้นเพื่อเป็นข้อความที่เข้ารหัสเอง
celtschk

2
@celtschk ตัดสินโดยสัญลักษณ์ OPs: หากโปรแกรมของคุณได้รับสองอินพุตให้เข้ารหัสอินพุตแรกในอินพุตที่สอง หากโปรแกรมได้รับอินพุตเดียวเท่านั้นให้แยกสตริงที่เข้ารหัสล่าสุดในอินพุตนั้น
Martin Ender

4
ควรจะมีวิธีกู้ P * จาก P ** หรือไม่? ถ้าไม่ทำไมต้องใช้ " P ** มีสองข้อความ - M และ M2 " ฉันขอโทษ แต่ถึงแม้ว่าความท้าทายนี้จะน่าสนใจสเป็คก็เป็นทางที่สับสนเกินไปสำหรับฉัน
Ilmari Karonen

คำตอบ:


8

Perl

นี่คือหนึ่งซับใน Perl เพียงเพราะมันเป็นไปได้

if($ARGV[0]){open(F,__FILE__);while(<F>){print;print"$ARGV[0]\n"if/^_/;}}else{print<DATA>;}
__DATA__

ข้อความจะถูกเขียนหลังจาก__DATA__ล่าสุดเป็นครั้งแรก


การแข่งขันที่ดีต่อสุขภาพและการแสดงออกทางเดียว
seequ

นั่นเป็นมูลค่าที่ค่อนข้างใหญ่ของที่คุณไปถึงที่นั่น
Gilles 'ดังนั้นหยุดความชั่วร้าย'

4

หลาม

คุณรู้อะไรไหม? ทำไมไม่ทำให้มันเป็นนิพจน์เดียว?

P = (lambda M,P=None:(lambda t:P[:74]+repr(M)[1:-1]+"'))"if P else M[74:-3])(''))
Pc = "(lambda M,P=None:(lambda t:P[:74]+repr(M)[1:-1]+\"'))\"if P else M[74:-3])(''))"
P2c = P('Hi there, mate!', Pc)
print "Encode tests:"
print " P2 = P('Hi there, mate!', Pc) =", P2c
exec 'P2 = ' + P2c
print " P2(\"Test 2's the best.\", P2c) =", P2("Test 2's the best.", P2c)

print "Decode tests:"
print "P2(P2) =", P2(P2c)
print "P(P2)  =", P(P2c)
print "P2(P)  =", P2(Pc)
print "P(P)   =", P(Pc)

ข้อความเก่า ฟังก์ชัน P รับอาร์กิวเมนต์ตามที่ระบุและส่งออกผลลัพธ์โค้ด / ถอดรหัสข้อความ

def P(data,func=None):
    text = ""
    if func:
        return func[:35]+data+'"\n'+'\n'.join(func.split('\n')[2:])
    return data[35:].split('\n')[0][:-1]

# The source code.
Pc = """def P(data,func=None):
    text = ""
    if func:
        return func[:35]+data+'"\\n'+'\\n'.join(func.split('\\n')[2:])
    return data[35:].split('\\n')[0][:-1]"""

P2c = P('Hi there, mate!', Pc)
print "Encode test:"
print "P('Hi there, mate!', P) ->"
print P2c

# This is outputted by P('Hi there, mate!', code-of-P)
def P2(data,func=None):
    text = "Hi there, mate!"
    if func:
        return func[:35]+data+'"\n'+'\n'.join(func.split('\n')[2:])
    return data[35:].split('\n')[0][:-1]

print "P2('Text 2', P2) -<"
print P2('Text 2', P2c)

print "Decode test:"
print "P2(P2) =", P2(P2c)
print "P(P2)  =", P(P2c)
print "P2(P)  =", P2(Pc)
print "P(P)   =", P(Pc)

2

JavaScript

var transform = function (p, m) {
    var _M_ = '';
    var source = arguments.callee.toString();
    var msgre = /(_M_ = ').*(';)/;
    var regex = new RegExp(source.replace(/[.*+?^$\[\]{}()\\|]/g, "\\$&").replace(msgre, "$1(.*)$2"));

    var a = p.toString().match(regex);

    if (!a) {
        throw "first argument must be a transform function"
    } else {
        a = a[1];
    }

    if (typeof m == "undefined") {
        return eval("[" + a.split("|")[0] + "]").map(x=>String.fromCharCode(x)).join("");
    } else {
        a = m.toString().split("").map(x => x.charCodeAt(0)) + (a.length ? "|" + a: a);
        return eval("(" + source.replace(msgre, "$1" + a + "$2") + ")");
    }
}

ไม่แน่ใจว่าฉันเข้าใจคำแถลงปัญหาอย่างถูกต้องหรือไม่: ตัวถอดรหัสของฉันจะถอดรหัสโปรแกรมใด ๆและส่งคืนข้อความล่าสุดที่เข้ารหัสในโปรแกรมที่กำหนด

รหัสทดสอบ:

P1 = transform(transform, "first message");
P2 = P1(P1, "second message");

console.log(P1(P1));
console.log(P2(P2));

console.log(P2(P1));
console.log(P1(P2));

// Unspecified behavior
console.log(transform(transform))

2

ชุด

@echo off

setLocal enableDelayedExpansion
for /f %%a in (%0) do set a=%%a

if "%~1"=="e" (
    set /a a+=1
    echo !a! %~2 >> %0
    echo message encoded as !a!
) else if "%~1"=="d" for /f "skip=12 tokens=1*" %%a in (%0) do if "%%a"=="%~2" echo %%b

goto :EOF

หมายเหตุ: goto :EOFมีความต้องการที่จะกลับรถหลังจากที่บรรทัดสุดท้ายของ

ใช้สองอินพุตจาก stdin สิ่งแรกคือสิ่งที่คุณต้องการทำ; eหรือd(เข้ารหัสและถอดรหัส) อินพุตที่สองขึ้นอยู่กับอินพุตแรก - ถ้าอินพุตแรกคืออินพุตeที่สองจะเป็นข้อความที่คุณต้องการเข้ารหัส - ถ้าเป็นdแล้วอินพุตที่สองจะเป็นหมายเลขของข้อความที่คุณต้องการถอดรหัส (ซึ่งจะ ได้รับหลังจากการเข้ารหัสข้อความ)

H:\uprof>ed.bat e "Just a message"
message encoded as 1

H:\uprof>ed.bat d 1
Just a message

0

งูเห่า

use System.Diagnostics
class Program
    var message as int[]? = nil
    def decode(program as String)
        temp = List<of String>(program.split('\n'))
        temp.insert(4, '\t\tEnvironment.exit(0)')
        temp.add('\t\tmessage = \'\'')
        temp.add('\t\tfor i in .message, message += Convert.toString(i to char)')
        temp.add('\t\tFile.writeAllText(\'message.txt\', message)')
        program = temp.join('\n')
        File.writeAllText('decode.cobra', program)
        process = Process()
        process.startInfo.fileName = 'cmd.exe'
        process.startInfo.arguments = '/C cobra decode.cobra'
        process.start
    def encode(message as String, program as String)
        temp = List<of String>()
        for i in message.toCharArray, temp.add(Convert.toString(i to int))
        message = '@' + Convert.toString(c'[')
        for n in temp.count-1, message += temp[n] + ','
        message += temp.pop + ']'
        temp = List<of String>(program.split('\n'))
        temp.insert(26,'\t\t.message = .message ? [message]')
        program = temp.join('\n')
        File.writeAllText('encode.cobra', program)
    def main
        #call methods here
        #.encode(message, program)
        #.decode(program)

ในขณะที่ความคิดนั้นเป็นเรื่องเล็กน้อยการดำเนินการของความคิดที่กล่าวมานั้นน้อยกว่ามาก

การเข้ารหัส

การเข้ารหัสข้อความในโปรแกรมจะเพิ่มสายทันทีหลังจากที่.message = .message ? x def mainบรรทัดนี้ตรวจสอบว่า.messageเป็นศูนย์หรือไม่ถ้าเป็นเช่นนั้นจะตั้งค่า.messageเป็นอาร์เรย์จำนวนเต็มที่มีค่ารหัสอักขระของอักขระแต่ละตัวในข้อความ การตรวจสอบและการกำหนดตำแหน่งศูนย์ให้หลีกเลี่ยงการเขียนทับข้อความใหม่ด้วยข้อความที่เก่ากว่า โปรแกรมใหม่ถูกบันทึกลงในencode.cobra

ถอดรหัส

การถอดรหัสโปรแกรมจะเพิ่มสามบรรทัดในตอนท้ายของวิธีการหลักซึ่งทำให้โปรแกรมแปลงรหัสถ่าน.messageเป็นสตริงซึ่งจะถูกบันทึกไว้message.txtเมื่อโปรแกรมใหม่ทำงาน จากนั้นโปรแกรมใหม่จะถูกบันทึกdecode.cobraและคอมไพเลอร์จะถูกเรียกใช้

decode.cobra ถูกใช้เหมือนไฟล์ชั่วคราวและไม่สามารถใช้เพื่อเข้ารหัสหรือถอดรหัสข้อความอื่นใช้ต้นฉบับหรือ encode.cobra

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.