dongwen3410 2015-07-28 06:53
浏览 49
已采纳

围棋练习之旅:rot13Reader

I'm trying to solve the Tour of Go exercise rot13Reader:

Here is my solution:

package main

import (
    "io"
    "os"
    "strings"
)

type rot13Reader struct {
    r io.Reader
}

func rot13(x byte) byte {
    switch {
    case x >= 65 && x <= 77:
        fallthrough
    case x >= 97 && x <= 109:
        x = x + 13
    case x >= 78 && x <= 90:
        fallthrough
    case x >= 110 && x >= 122:
        x = x - 13
    }
    return x
}

func (r13 *rot13Reader) Read(b []byte) (int, error) {
    n, err := r13.r.Read(b)
    for i := 0; i <= n; i++ {
        b[i] = rot13(b[i])
    }
    return n, err
}

func main() {
    s := strings.NewReader("Lbh penpxrq gur pbqr!")
    r := rot13Reader{s}
    io.Copy(os.Stdout, &r)
}

It returns You prnpxrq tur poqr!, that means only the first word of "Lbh penpxrq gur pbqr!" is cracked. How can I crack the whole sentence?

  • 写回答

13条回答 默认 最新

  • douduan9129 2015-07-28 07:07
    关注

    EDIT:

    Basically your solution is good and works, you just mistyped 1 character:

    case x >= 110 && x >= 122:
    

    Change it to:

    case x >= 110 && x <= 122:
    

    Your input and output:

    Lbh penpxrq gur pbqr!
    You prnpxrq tur poqr!
    

    There is change in every word. The problem is not that only the first word is read and decoded, the problem is in your decoding algorithm.

    In ROT13 if shifting goes outside of the letter range, you have to start from the beginning of the alphabet (or at the end). For example shifting 'N' would be 'Z' + 1, so it becomes 'A', the first letter. See this simple character mapping:

    ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz
    NOPQRSTUVWXYZABCDEFGHIJKLMnopqrstuvwxyzabcdefghijklm
    

    So what you should do is after shifting by 13, if the letter goes outside of the alphabet, shift it by -26 (number of letters in the English alphabet) which has the desired effect (that after the last letter you continued from the first).

    An example solution:

    func rot13(x byte) byte {
        capital := x >= 'A' && x <= 'Z'
        if !capital && (x < 'a' || x > 'z') {
            return x // Not a letter
        }
    
        x += 13
        if capital && x > 'Z' || !capital && x > 'z' {
            x -= 26
        }
        return x
    }
    

    And its output:

    You cracked the code!
    

    Try it on the Go Playground.

    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论
查看更多回答(12条)

报告相同问题?

悬赏问题

  • ¥15 关于#MATLAB#的问题,如何解决?(相关搜索:信噪比,系统容量)
  • ¥500 52810做蓝牙接受端
  • ¥15 基于PLC的三轴机械手程序
  • ¥15 多址通信方式的抗噪声性能和系统容量对比
  • ¥15 winform的chart曲线生成时有凸起
  • ¥15 msix packaging tool打包问题
  • ¥15 finalshell节点的搭建代码和那个端口代码教程
  • ¥15 Centos / PETSc / PETGEM
  • ¥15 centos7.9 IPv6端口telnet和端口监控问题
  • ¥20 完全没有学习过GAN,看了CSDN的一篇文章,里面有代码但是完全不知道如何操作