leet讲译者关键的bug

时间:2014-01-15 07:24:14

标签: javascript

昨天我发布了一个关于我的leet说JavaScript应用程序的问题 - Making a leet speak translator

今天关于那个老化的帖子。我改进了代码并最终遇到了一个严重的问题。

这是应用程序 - http://jsbin.com/azIQiVi/1

乍一看,你会认为它的工作正常。但实际上并非如此。

如果附加了一些标点字符,例如"hacker""cool"dot等,则无法更改commanewline等字词。

例如,如果你写"He is a cool hacker",它会将其转换为"h3 15 4 kewl h4x0r",这很好。

但是如果你写"He is a cool hacker."(请注意全程),它会将其转换为"h3 15 4 kewl h4ck3r."

应将其转换为"h3 15 4 kewl h4x0r."

希望你明白我的意思。

我无法解决这个问题,不知道吗?

这是代码:

// http://en.wikipedia.org/wiki/Leet
// http://www.catb.org/jargon/html/crackers.html

var words = {
  "am": "m",
  "are": "r",
  "at": "@",
  "thanks": "thx",
  "your": "ur",

  "cool": "kewl",
  "defeated": "pwned",
  "dude": "d00d",
  "fear": "ph33r", // or ph34r
  "fool": "f00",
  "freak": "phreak",
  "hacker": "h4x0r",
  "lamer": "l4m3r",
  "mad": "m4d",
  "newbie": "n00b",
  "own": "pwn",
  "phone": "fone",
  "porn": "pr0n", // or n0rp
  "rocks": "roxxorz",
  "skill": "sk1llz",
  "sucks": "sux0r",
  "the": "t3h",
  "uber": "ub3r", // or |_|83r
  "yay": "w00t",
  "yo": "j0",
  "you": "j00" // or U
};
var alphabets = {
  "a": "4",
  "b": "8",
  "e": "3",
  "f": "ph",
  "g": "6", // or 9
  "i": "1", // or |
  "o": "0",
  "s": "5",
  "t": "7" // or +

  // advanced
  // "c": "(", // or k or |< or /<
  // "d": "<|",
  // "h": "|-|",
  // "k": "|<", // or /<
  // "l": "|", // or 1
  // "m": "|\\/|",
  // "n": "|\\|",
  // "p": "|2",
  // "u": "|_|",
  // "v": "/", // or \/
  // "w": "//", // or \/\/
  // "x": "><",
  // "y": "'/"
};

var elite = document.getElementById("elite"),
  leet = document.getElementById("leet"),
  randomcase = document.getElementById("randomcase");

function changeLetters(text) { // change letters
  text = text || elite.value.toLowerCase();
  for (var i = 0; i < text.length; i++) {
    if (alphabets[text[i]]) {
      text = text.replace(text[i], alphabets[text[i]]);
    }
  }
  return text;
}

function changeWords() { // change special words
  var wordsArr = changeLetters().split(" ");
  for (var i = 0; i < wordsArr.length; i++) {
    if (words[wordsArr[i]]) {
      wordsArr[i] = words[wordsArr[i]];
    }
  }
  return wordsArr.join(" "); // text
}

function randomizeCase() { // RANdOMiZE CAsE
  var text = changeWords();
  for (var i = 0; i < text.length; i++) {
    if (Math.random() > 0.5) {
      text = text.replace(text[i], text[i].toUpperCase());
    } // else keep lower case
  }
  return text;
}

(function() { // l33t the words object
  for (var word in words) {
    if (words.hasOwnProperty(word)) {
      words[changeLetters(word)] = words[word];
      delete words[word];
    }
  }
}());

function tol33t() {
  leet.value = randomcase.checked ? randomizeCase() : changeWords();
}

elite.addEventListener("input", tol33t);
document.getElementById("btn").addEventListener("click", tol33t);

1 个答案:

答案 0 :(得分:1)

通过空格分割单词的方法(正如您已经注意到的那样)不适用于标点符号。因此,更好的方法是逐个识别单词并注意标点符号。

这个使用字符串类型的replace()函数。它通过字典中相应的单词替换任何找到的匹配项。正则表达式模式[^,\.\s]+检测不是逗号,点或空格(空格,制表符,换行符等)的任何字符组合。

function changeWords() {
    // change special words 
    return changeLetters().replace(
        /[^,\.\s]+/g,
        function(m) {
            return words[m] ? words[m] : m;
        }
    );
}