Pisanie na klawiaturze telefonu komórkowego
To pytanie zostało zadane jakiś czas temu, ale zostało zamknięte z powodu złej specyfikacji. Ponawiam to z lepszymi specyfikacjami. To pytanie jest powiązane, ale idzie w przeciwnym kierunku.
Przed pojawieniem się T9, aby wpisać znak w wiadomości tekstowej, musiałeś kilkakrotnie nacisnąć jeden z klawiszy numerycznych, aby uzyskać żądany znak. Dla porównania, oto standardowe odwzorowanie:
+-------+-------+-------+
| 1 | 2 | 3 |
| .?!1 | ABC2 | DEF3 |
+-------+-------+-------+
| 4 | 5 | 6 |
| GHI4 | JKL5 | MNO6 |
+-------+-------+-------+
| 7 | 8 | 9 |
| PQRS7 | TUV8 | WXYZ9 |
+-------+-------+-------+
| * | 0 | # |
| ← |SPACE 0| → |
+-------+-------+-------+
*
jest backspace, 0
jest spacją ( ' '
) lub liczbą 0
i #
potwierdza bieżący znak. Dla uproszczenia wszystkie znaki są pisane wielkimi literami.
Po naciśnięciu klawisza kilka razy wybrany przez cykle znaków możliwych znaków dla tego klucza: 2 -> A
, 22 -> B
, 222 -> C
, 2222 -> 2
, 22222 -> A
, i tak dalej. Zauważ, że ponieważ *
ma tylko jedną opcję, wielokrotne naciskanie powoduje wprowadzenie wielu cofnięć. Naciśnięcie #
wiele razy z rzędu nie ma wpływu. Końcowanie nie #
jest konieczne.
Dodatkowo, jeśli inny klawisz zostanie naciśnięty natychmiast po naciśnięciu klawisza, poprzednie naciśnięcie klawisza zostanie automatycznie potwierdzone. A zatem,223
jest funkcjonalnie identyczny z 22#3
.
Wyzwanie polega na przetłumaczeniu serii naciśnięć klawiszy na odpowiedni ciąg znaków wyświetlany przez telefon komórkowy.
Przykłady
8#99999#055#33#999#22#666#2#777#3#1 -> T9 KEYBOARD
4433555#55566609666666677755533*3111 -> HELLO WORLD!
7##222#222**7#222#4 -> PPCG
00#0#00 -> 0 0
Zasady
- To jest golf golfowy , więc wygrywa najkrótsze prawidłowe rozwiązanie (w bajtach)
- Zwycięska odpowiedź zostanie wybrana za tydzień
- Standardowe luki są zabronione
- Twoja odpowiedź może mieć postać pełnego programu, funkcji o nazwie lub funkcji anonimowej, pobierając dane wejściowe i generując dane wyjściowe za pomocą jednej ze standardowych metod
Tabela liderów
Fragment kodu na dole tego postu generuje tabelę wyników na podstawie odpowiedzi a) jako lista najkrótszych rozwiązań dla każdego języka oraz b) jako ogólna tabela wyników.
Aby upewnić się, że twoja odpowiedź się pojawi, zacznij od nagłówka, korzystając z następującego szablonu Markdown:
## Language Name, N bytes
gdzie N
jest rozmiar twojego zgłoszenia. Jeśli poprawić swój wynik, to może zachować stare porachunki w nagłówku, uderzając je przez. Na przykład:
## Ruby, <s>104</s> <s>101</s> 96 bytes
Jeśli chcesz umieścić w nagłówku wiele liczb (np. Ponieważ twój wynik jest sumą dwóch plików lub chcesz osobno wymienić kary za flagi tłumacza), upewnij się, że rzeczywisty wynik jest ostatnią liczbą w nagłówku:
## Perl, 43 + 2 (-p flag) = 45 bytes
Możesz także ustawić nazwę języka jako link, który pojawi się we fragmencie:
## [><>](http://esolangs.org/wiki/Fish), 121 bytes
<style>body { text-align: left !important} #answer-list { padding: 10px; width: 290px; float: left; } #language-list { padding: 10px; width: 290px; float: left; } table thead { font-weight: bold; } table td { padding: 5px; }</style><script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script> <link rel="stylesheet" type="text/css" href="//cdn.sstatic.net/codegolf/all.css?v=83c949450c8b"> <div id="language-list"> <h2>Shortest Solution by Language</h2> <table class="language-list"> <thead> <tr><td>Language</td><td>User</td><td>Score</td></tr> </thead> <tbody id="languages"> </tbody> </table> </div> <div id="answer-list"> <h2>Leaderboard</h2> <table class="answer-list"> <thead> <tr><td></td><td>Author</td><td>Language</td><td>Size</td></tr> </thead> <tbody id="answers"> </tbody> </table> </div> <table style="display: none"> <tbody id="answer-template"> <tr><td>{{PLACE}}</td><td>{{NAME}}</td><td>{{LANGUAGE}}</td><td>{{SIZE}}</td><td><a href="{{LINK}}">Link</a></td></tr> </tbody> </table> <table style="display: none"> <tbody id="language-template"> <tr><td>{{LANGUAGE}}</td><td>{{NAME}}</td><td>{{SIZE}}</td><td><a href="{{LINK}}">Link</a></td></tr> </tbody> </table><script>var QUESTION_ID = 61545; var ANSWER_FILTER = "!t)IWYnsLAZle2tQ3KqrVveCRJfxcRLe"; var COMMENT_FILTER = "!)Q2B_A2kjfAiU78X(md6BoYk"; var OVERRIDE_USER = 45941; var answers = [], answers_hash, answer_ids, answer_page = 1, more_answers = true, comment_page; function answersUrl(index) { return "https://api.stackexchange.com/2.2/questions/" + QUESTION_ID + "/answers?page=" + index + "&pagesize=100&order=desc&sort=creation&site=codegolf&filter=" + ANSWER_FILTER; } function commentUrl(index, answers) { return "https://api.stackexchange.com/2.2/answers/" + answers.join(';') + "/comments?page=" + index + "&pagesize=100&order=desc&sort=creation&site=codegolf&filter=" + COMMENT_FILTER; } function getAnswers() { jQuery.ajax({ url: answersUrl(answer_page++), method: "get", dataType: "jsonp", crossDomain: true, success: function (data) { answers.push.apply(answers, data.items); answers_hash = []; answer_ids = []; data.items.forEach(function(a) { a.comments = []; var id = +a.share_link.match(/\d+/); answer_ids.push(id); answers_hash[id] = a; }); if (!data.has_more) more_answers = false; comment_page = 1; getComments(); } }); } function getComments() { jQuery.ajax({ url: commentUrl(comment_page++, answer_ids), method: "get", dataType: "jsonp", crossDomain: true, success: function (data) { data.items.forEach(function(c) { if (c.owner.user_id === OVERRIDE_USER) answers_hash[c.post_id].comments.push(c); }); if (data.has_more) getComments(); else if (more_answers) getAnswers(); else process(); } }); } getAnswers(); var SCORE_REG = /<h\d>\s*([^\n,<]*(?:<(?:[^\n>]*>[^\n<]*<\/[^\n>]*>)[^\n,<]*)*),.*?(\d+)(?=[^\n\d<>]*(?:<(?:s>[^\n<>]*<\/s>|[^\n<>]+>)[^\n\d<>]*)*<\/h\d>)/; var OVERRIDE_REG = /^Override\s*header:\s*/i; function getAuthorName(a) { return a.owner.display_name; } function process() { var valid = []; answers.forEach(function(a) { var body = a.body; a.comments.forEach(function(c) { if(OVERRIDE_REG.test(c.body)) body = '<h1>' + c.body.replace(OVERRIDE_REG, '') + '</h1>'; }); var match = body.match(SCORE_REG); if (match) valid.push({ user: getAuthorName(a), size: +match[2], language: match[1], link: a.share_link, }); else console.log(body); }); valid.sort(function (a, b) { var aB = a.size, bB = b.size; return aB - bB }); var languages = {}; var place = 1; var lastSize = null; var lastPlace = 1; valid.forEach(function (a) { if (a.size != lastSize) lastPlace = place; lastSize = a.size; ++place; var answer = jQuery("#answer-template").html(); answer = answer.replace("{{PLACE}}", lastPlace + ".") .replace("{{NAME}}", a.user) .replace("{{LANGUAGE}}", a.language) .replace("{{SIZE}}", a.size) .replace("{{LINK}}", a.link); answer = jQuery(answer); jQuery("#answers").append(answer); var lang = a.language; lang = jQuery('<a>'+lang+'</a>').text(); languages[lang] = languages[lang] || {lang: a.language, lang_raw: lang.toLowerCase(), user: a.user, size: a.size, link: a.link}; }); var langs = []; for (var lang in languages) if (languages.hasOwnProperty(lang)) langs.push(languages[lang]); langs.sort(function (a, b) { if (a.lang_raw > b.lang_raw) return 1; if (a.lang_raw < b.lang_raw) return -1; return 0; }); for (var i = 0; i < langs.length; ++i) { var language = jQuery("#language-template").html(); var lang = langs[i]; language = language.replace("{{LANGUAGE}}", lang.lang) .replace("{{NAME}}", lang.user) .replace("{{SIZE}}", lang.size) .replace("{{LINK}}", lang.link); language = jQuery(language); jQuery("#languages").append(language); } }</script>
2 -> A
,22 -> B
...,2222 -> A
....) nie pozwala na tworzenie żadnych liczb.Odpowiedzi:
K5, 112 bajtów
To jest naprawdę bałagan, ale myślę, że jest sporo miejsca na grę w golfa.
Najpierw musimy zbudować tabelę odnośników dla mapy klawiszy. Istnieją klucze z przypisanymi do nich 2, 4 i 5 znakami, więc wypełnienie każdego wpisu wartością do 20 upraszcza proces cyklicznego indeksowania tej tabeli później:
Następnie podzielę dane wejściowe na przebiegi:
Upuszczaj dowolne # przebiegów i usuwaj końcowe biegi za każdym razem, gdy napotykam *:
A potem jestem gotów po prostu zaindeksować tę tabelę wyszukiwania na podstawie długości i pierwszego elementu każdego uruchomienia.
Wszyscy razem:
Edytować:
Zapisz 5 bajtów:
źródło
(20#'((" ";".?!"),0 3 6 9 12 15 19 22_`c$65+!26),'$!10)
do(20#'((" ";".?!"),((3*!6),19 22)_`c$65+!26),'$!10)
.Python 2,
230206 bajtówTen tworzy funkcję f, która przyjmuje ciąg naciśnięć klawiszy jako argument i zwraca odpowiedni ciąg, który wyświetliby telefon komórkowy. Zdarza się również wziąć opcjonalny drugi argument jako klucze mapowania słownika na odpowiadające im znaki, np. {"0": "0", "1": ".?! 1", ...} .
Najpierw ciąg naciśnięć klawiszy jest grupowany przez powtarzanie znaków, np. [„8”, „#”, „99999”, „#”, ...] . Następnie pierwszy znak każdej grupy jest mapowany w słowniku przekazywanym jako drugi argument, np. 9 mapuje na WXYZ9 . Na koniec długość grupy jest używana jako przesunięcie wartości ze słownika.
Zauważ, że offset musi używać modulo na długości grupy powtarzających się znaków, ponieważ naciśnięcia klawiszy mogą się zmieniać. Zauważ również, że znak # jest mapowany na \ 0 i usuwany tylko na końcu, ponieważ 99 # 99 to nie to samo co 9999 .
Oto wynik funkcji dla każdego z przykładów w pytaniu:
źródło
JavaScript,
214184168162 bajtówPrawdopodobnie można to nieco zmniejszyć, ale jestem bardzo zadowolony z wyniku. Dzieli znaki na powtarzające się grupy jednego lub więcej, a następnie przechodzi przez tablicę, mapując każdy znak na jego wartość w haszu i dodając go do końcowego ciągu. Jeśli natrafi na dowolną liczbę „#”, ignoruje ją. Jeśli natrafi na dowolne „*”, usuwa ich liczbę z końca ostatniego ciągu.
źródło
Python 2, 237 bajtów
Korzystanie ze słownika cr3, ale bez re.
źródło
Python 2, 265 bajtów
To zdecydowanie za długo. IO: standardowe, standardowe.
źródło