文字化けした電話番号


19

ボイスメールメッセージをどのように受け取り、その人の接続がうまくいかなかったことは知っていて、電話をかける方法を見つけようとしていますが、それが「5」か「8」かはわかりません前記?

それがこの挑戦です。

良いニュースは、発信者が番号を2回読み上げたことですが、両方の場所で文字化けしています。

プログラムは次のように入力する必要があります。

5551231234 / 5551231234

最初の10桁が電話番号がボイスメールで最初に言われ、2番目のセットが2回目に言われたときです。のみ...次のようになります。

555?ABC1_36? / 55?522_1?234
  • 数字に疑問符が続くことは、それがその数字の最良の推測であることを意味します(例えば、「5?」は「おそらく5、繰り返しと比較」を意味します)。
  • アンダースコアは、既知の欠落している数字を示します。これは、静的によってファジングされすぎて解読できないものです。
  • 文字はそれだけです:文字。それらをそれぞれの数字として扱います
    • ABC-> 2、DEF-> 3、GHI-> 4、JKL-> 5、MNO-> 6、PQRS-> 7、TUV-> 8、WXYZ-> 9
    • サンプル入力はすべて大文字を使用します(ToUpper()呼び出しは安全に省略できます)
    • 言語が小文字でうまく機能する場合は、入力に小文字を自由に使用し、ToLower()呼び出しを省略できます。あなたの答えに注意してください。

さらに、次の判断呼び出しを想定できます。

5? / _     -> 5  //5 is the best guess we have, use it
5? / 5?    -> 5  //uncertain, but matching
5? / 4?    -> ?  //conflict
 5 / 4     -> ?  //conflict
5? / 4     -> 4  //solid information overrides possible value
 5 / 4?    -> 5  //solid information overrides possible value
 _ / _     -> ?  //no information available

さらに、すべての入力に疑問符を除く10桁の電話番号が含まれると想定できます。10桁以外の入力(例1234567 / 1234567:)は、解決不能(誤った出力)として処理されるか、エラーをスローします。

入力

上記の1行の文字0-9A-Z _?/

出力

1つの有効な10桁の電話番号に解析できる場合は、電話番号を出力します。それ以外の場合は、何らかの形のエラー表示(たとえば、-1、false、または空行)を出力します。

いつものように最短の勝利。

サンプル入力:

1234567890 / 1234567890
1234567890? / 1234567890
123456789_ / 1234567890
1234567890? / 123456789_
1234567890 / 1234567890?
1234567890 / 123456789_
123456789_ / 1234567890?
1234567890? / 1234567890?
1234567890? / 1234567891?
123456789_ / 123456789_
555CALLUS1 / 5552255871
404_12?6039 / 4041?1560_9
_GETREVENGE / 16?36?_2838_
1?691460_50 / 16_14609?50
61?08977211 / 612?897725?1
40?0INSTA__ / 8?00_NSTI?LL
3985_534?10 / 39?8?5053_10
7__7294?737 / 7797299?_37
28?897_384?1 / _8?89763861
271168090_ / 27116800?09
6802?148343 / 67?01148343
94_11628?2?6? / 9491162_47?
17?4285_689 / 1__26?52689
6_311?95_38 / 6731194?7?38
380?7DRAGON / 3807378?5?66
4?647_93236 / 5646?6?9__36
365?268898_ / 366267?7?984
GRATEDBATE / IRATEDBATE
5307_079?93 / ____8_____
535_3_0255 / 52?5_3_024?5
55_____088 / 54?2397207?7?
6_48398_95 / _946?398?6_5?
_0_312_3_1 / 81?53123?1?71
____1_____ / 64?255?508?61
8427820607 / 6?424?8?__6?07
50_3707__6 / 52?8375?74?56
615___8255 / 62?526?983?2?1?
__652618__ / 8365261__0
149___933_ / 1_9677?92?31
___7?281562 / 3438?28154?2
5?7?7?___8?3?7?4 / 57_855837_
605_272481 / 605427__81
86?569__731 / 88560?0?7721
1__91654?15 / 17?9?9165715
800NWABODE / 80069ABI?DE
8___9017_0 / 8_2494?12?9_
_024?5?91?470 / 304?17908?7_
42510704_2 / 4_51070492
9338737_89 / 93_873PLUS
327762_401 / 327_MASH01
33093_2058 / 3309_12058
4061_33578 / 40619_3578
559_383197 / 559938_197
94_9746084 / 9459746_84
1_37655238 / 163POLKA_T
_672FRIZZY / 767237499_
8_76318872 / TIP63188_2
51_8404321 / 5178404_21
358_030314 / 358603_314
2597_85802 / 25979_5802
77141_1408 / 7714_91408
330858_457 / 330_586457
4686079_39 / 46_6079239
86457508_6 / 8_45750826
523226626_ / _23BANNANA
_ISSY_ISSY / 44__9548?79?
6?00B_YJILT / 800289KILL?
2?52803___0 / 1526?0390?61?
FI?ND___T?HE / EAS?T?EREGGS?
0_231?95_38 / 0723194?7?38
0?647_39236 / 0646?6?3__36
025?267798_ / 06?6265?9?984
0061_33578 / _0619_3578

可能性のあるすべてのエッジケース(最初の11エントリ)がカバーされることを保証しただけですが、それ以外はほぼランダムです。

更新

下部に4つのエントリが追加され、先頭にゼロが追加されます(ジョナサンアランの提案)。

サンプル入力の正しい出力:

https://pastebin.com/gbCnRdLV

Jonathan Allanのエントリからの出力に基づいています(フォーマットされた出力が理想的でした)。


入力をで区切られた単一の文字列として取得する" / "必要がありますか、それとも単に2つの標準入力として取得できますか?
L3viathan

@ L3viathan私はもともと、単一の文字列を取る必要があると考えていました。
Draco18s

7
Draco18s @つの文字列は、チャレンジには何も持っていません
fənɛtɪk

1
@ fəˈnɛtɪkサンドボックスでは誰も何も言いませんでしたが、入力ペアの使用に反対することはありません。それは私が最初に考えた方法でした。
Draco18s

1
電話番号に文字を使用してボイスメールを残すのは誰ですか?!
ジョナサンアラン

回答:


3

ゼリー、84 バイト

+4バイト-おそらくすべての場合で同じように動作するはずなので、キーパッドのルックアップ整数をを使用して数字に戻しました+49Ọ

”?e‘ḣ@µ”_eḤ‘ẋ@
;Ṃµ68DṬ+3RØAṁẇ@€FT+49Ọȯµ€Fṡ2i”?Ḃ$ÐḟÇ€
ḟ⁶ṣ”/Ç€ZLÐṂ€Q€LỊ$ÐfF€Ḣ€ḟ”_µL⁼⁵ȧ

指定された形式の文字列を受け取り、文字のリストとして電話番号を返す関数、または無効な場合はゼロ。プログラムとして、これは文字列であるかのように出力されます。

それが機能する方法は、彼らがより多くの回数
(例えば"123456789_ / 123456789_ / 1234567890")を繰り返すことができ
ます...またはそれを一度だけ言っても、定義されたロジックが適用されます。

オンラインでお試しください!または、すべてのサンプル入力を参照してください。

どうやって?

”?e‘ḣ@µ”_eḤ‘ẋ@ - Link 1, helper to vary the length of a 2-slice: list s
”?             - literal '?'
  e            - exists in s                   (1 or 0)
   ‘           - increment                     (2 or 1)
    ḣ@         - head with reversed @rguments  (s or s[:1] - removes 2nd value if not '?')
      µ        - monadic chain separation, call that t
       ”_      - literal '_'
         e     - exists in t                   (1 or 0)
          Ḥ    - double                        (2 or 0)
           ‘   - increment                     (3 or 1)
            ẋ@ - repeat t that many times      (t*3 or t - [`_`]->['_','_','_'])

;Ṃµ68DṬ+3RØAṁẇ@€FT+49Ọȯµ€Fṡ2i”?Ḃ$ÐḟÇ€ - Link 2, reformat a phone number: char list of [0-9][A-Z], p
;                                     - concatenate p with
 Ṃ                                    - minimum of p - (?<_<0<1<...<9<A<...<Z - never "?" however, since it only follows a digit.)
                                      -   - this is simply to make a 2-slice with the last character on the left, as used at the very end of this link.
  µ                                   - monadic chain separation call that q
                       µ€             - monadic chain separation, for €ach v in q do:
   68                                 -   literal 68
     D                                -   cast to a decimal list -  [6,8]
      Ṭ                               -   untruth                -  [0,0,0,0,0,1,0,1]
       +3                             -   add 3                  -  [3,3,3,3,3,4,3,4]
         R                            -   range                  -  [[1,2,3],[1,2,3],[1,2,3],[1,2,3],[1,2,3],[1,2,3,4],[1,2,3],[1,2,34]]
          ØA                          -   uppercase alphabet     -  ABCDEFGHIJKLMNOPQRSTUVWXYZ
            ṁ                         -   mould like the range ^ -  [ABC,DEF,GHI,JKL,MNO,PQRS,TUV,WXYZ]
             ẇ@€                      -   sublist v exists in that? for €ach, with reversed @rguments
                F                     -   flatten        (e.g. 'E' -> [0,1,0,0,0,0,0,0]; '4' -> [0,0,0,0,0,0,0,0]
                 T                    -   truthy indexes (e.g. 'E' -> [2]; '4' -> [])
                  +49                 - add 49
                     Ọ                - cast to character
                      ȯ               -   or             (e.g. 'E' -> [3]; '4' -> '4')
                         F           - flatten
                          ṡ2          - all slices of length 2
                                 Ðḟ   - filter discard if:
                                $     -   last two links as a monad:
                            i         -     first index of
                             ”?       -     literal '?'   (first index returns 0 if none exists)
                               Ḃ      -   mod 2 (so this filter discards pairs starting with '?')
                                   Ç€ - call the last link (1) as a monad for €ach slice

ḟ⁶ṣ”/Ç€ZLÐṂ€Q€LỊ$ÐfF€Ḣ€ḟ”_µL⁼⁵ȧ - Main link: string (or char list) s
ḟ                               - filter discard any:
 ⁶                              - literal ' '
  ṣ                             - split on:
   ”/                           - literal '/'
     Ç€                         - call the last link (2) as a monad for €ach
       Z                        - transpose
         ÐṂ€                    - filter, for €ach, keep items with minimal:
        L                       -   length
            Q€                  - de-duplicate €ach
                 Ðf             - filter keep items with:
                $               - last two links as a monad:
              L                 -   length
               Ị                -   insignificant? (=1 effectively here)
                   F€           - flatten €ach
                     Ḣ€         - head €ach
                       ḟ        - filter discard any of:
                        ”_      -   literal '_'
                          µ     - monadic chain separation, call that r
                           L    - length(r)
                             ⁵  - literal 10
                            ⁼   - equal?
                              ȧ - and r (0 if r did not result in a 10-digit list, else r)

エラーがあるように見えますが、55_____088 / 54?2397207?7?解決する必要があります。5523972088欠落している数字はすべて存在し、右側の不確実な数字は左側に表示されます。ただし、単純なケースはすべて実行されます。
-Draco18s

ああ、冗長フィルターだと思っていたものを削除しましたが、そうではありませんでした。修正...
ジョナサン・アラン

そこに行ったことがありますが、それはゴルフではありませんでした!;)
Draco18s

しばらく時間がかかりました(テスト中に別のバグが見つかりました)が、修正するときにフィルターを追加し直すのと同じバイトカウントに戻しました(ただし)。
ジョナサンアラン

@ Draco18s-すべてがあなたに似合っていますか?問題のテストケースに期待される出力を提供するか、または無効なものを単に分離することができます。
ジョナサンアラン

7

パイソン2314の 307 274バイト

lambda s:g(*''.join(q<n<"["and`(int(n,36)-4-(n>"R")-(n>"Y"))//3`or n for n in s).split(" / "))
def g(a,b,s=str.startswith):
 if b:c,d,e,f=a[0],a[1:],b[0],b[1:];b=(c==e and[c,q][c=="_"]or"_"in c+e and min(c,e)or[q,c,e][s(f,q)-s(d,q)])+g(d[s(d,q):],f[s(f,q):])
 return b
q="?"

オンラインでお試しください!


5

Python 3、549 530 509 453 449 410 406 394 393 393 391バイト

これは改善できると確信していますが、開始点です。

def f(e,z,q="?",u=str.isnumeric):
 if e+z in(e,z):return""
 o,O,t,T,*x=e[0],e[1:2],z[0],z[1:2],e[1:],z[1:]
 if"?"in o+t:return f([e,x[0]][o==q],z)
 if u(o):
  if u(t):return t+f(*x)if O==q!=T else o+f(*x)if o==t or T==q!=O else 1
  return o+f(*x)
 if u(t):return t+f(*x)
def g(s):
 for a,b in zip(map(chr,range(65,91)),"2223334445556667777888999"):s=s.replace(a,b)
 return f(*s.split(" / "))

私は使っています str.translate文字、ラッパー関数のためにg、私はそれらを先の形式で入力を行うこと。実際の関数fは再帰的であり、あいまいな入力では失敗します。私はまだそこにたくさんの繰り返しがありますので、改善の余地があると確信しています。

改善点:

  • 条件を組み合わせて19バイトを節約
  • 三値で21バイトを節約しました
  • @TuukkaXのおかげで、手動辞書の代わりに辞書内包表記を使用して56バイトを節約しました
  • @ovsによって提案されたメソッドに切り替えることで4バイトを節約しましたが、@ TuukkaXが改善されました
  • @ovsからの改善で38バイトを節約しました(そして最後の取り外し可能な空白を削除しました)
  • str.isnumericキーワード引数に定義を入れることで4バイト節約
  • 結合された比較演算子で12バイトを節約(例T==q!=O
  • に変更することで1バイトを節約not(e or z)しましたe+z in(e,z)
  • 頻繁に使用されるものを保存することで2バイトを節約 (E,Z)

これには、最上行のデフォルトを含まない辞書内包が含まれています。私は3のシーケンスが嫌いですが、それらは数学に置き換えられるかもしれません。
Yytsi


@ovsいいね。map(chr,range(65,91))ただし、アルファベットは変更できます。
Yytsi

2
RE:これを評判を放棄するコミュニティwikiにすると、コンセンサスはありません。親切な助けを受け入れ、あなたが持っているように信用してください。
ジョナサンアラン

1
私はここに戻るたびにこの答えが短くなると誓います:D
Draco18s

3

JavaScript(ES6)、180 190 188バイト

編集:+10 +9バイトで偽の出力ルールに準拠


カリー化構文の2つの入力文字列を受け取ります(a)(b)false推測された電話番号を表す文字列またはいずれかを返します。

a=>b=>!(s=(F=a=>a.match(/(.\??)|_/g).map(([x,y])=>(x<=9?++x:parseInt(x,36)*.32-(x>'Y'))|(x!='_'&!y)*16))(a).map((x,i)=>(x=(d=x^(y=F(b)[i]),x>y)?x:y)&&(d&16|!(d%x))?--x&15:a).join``)[10]&&s

使い方

ステップ#1-入力文字列の解析

最初にF()、次の規則を適用して、文字列を整数の配列に変換する関数を定義します。

  • アンダースコアは0に変換されます
  • 数字Nまたは同等の文字は(N + 1)OR 16に変換されます(例:「2」→19、「R」→24)
  • 数字Nまたは同等の文字に続いて質問マークがN + 1に変換されます(例:「2?」→3、「R?」→8)

これは、次のように逆に解釈できます。

  • 0不明
  • [ 1 .. 10 ]信頼できない
  • [ 17 .. 26 ]信頼できる

当社は、適用F()の両方にab。これにより、整数のペア(x、y)が得られます、2つの可能な解釈に対応する、電話番号の各桁られます。

ステップ#2-数字を推測する

各ペア(x、y)について、次を計算します。

  • d = x XOR y
  • x = MAX(x、y)信頼できない値よりも信頼できる値が常に優先される

もし x == 0の、両方の入力がアンダースコア文字であることを意味します。したがって、この場合、数字は不明です。

もし !x = 0の次の条件のいずれかに該当する場合、我々は安全に数字を推測することができます:

condition       | interpretation
----------------+------------------------------------------------------
(d AND 16) != 0 | one input is unreliable and the other one is reliable
d == 0          | both inputs are identical
d == x          | one input is an underscore

最後の2つの条件は、次のものとマージできます。 !(d % x)。したがって、最終的な式:

x && (d & 16 || !(d % x))

trueの場合、xを変換しますを計算することによって推測桁に背を(X - 1)AND 15

テストケース

(コンソールスニペットはこれ以上の出力履歴をサポートできないため、最初の50個のみです。)


1234567890? / 1234567890?に解決する必要があります1234567890。現時点123456789?では、入力よりも情報量が少ないコードが出力されます。Assume: 5? / 5? -> 5 //uncertain, but matching
-Draco18s

@ Draco18s私が述べたことに反して、51のテストケースを含めました。したがって、最初の行は削除され、すべてが1行ずつシフトしました。(現在修正済みです。ごめんなさい。)
アーナルド

ああ。それでも、それらのテストケースに対して何らかの偽値またはエラー値を出力するはずです。しかし、それ以外は良さそうです。
Draco18s

2

Perl 5、211バイト

...インデントおよび\ n改行なし

@i=map{y/ABCDEFGHIJKLMNOPQRSTUVWXYZ/22233344455566677778889999/;$_}split' / ',shift;
print map{
  $_=join'',map{s,(\d\??|_),,;$1}@i;
  /((\d)\??\2\??|(\d)\??_|_(\d)\??|(\d)\d\?|\d\?(\d))$/;$2//$3//$4//$5//$6//'?'
}1..10

オンラインでお試しください!


83652618?0何らかの偽値やエラー値ではなく、「できる限り最高」を返すように見えます()。
-Draco18s

私が間違っていないなら、それはパズルが望んだものです。「さらに次の判断の呼び出しを想定することができます」という見出しの下のケースを見てください。か否か?
Kjetil S.

申し訳ありませんが、返信の通知はありません(言及なし)。私は判断の呼び出しのために行わのだセクションでは、使用して?[出力]セクションにフォールスルーすべき不足している情報を、解決する方法がないことを示すために:...Otherwise output some form of error indication (e.g. -1, false, or an empty line).
Draco18s

2

網膜、150の 140 136バイト

Kritixi Lithosのおかげで数バイト節約

T`?L`#22233344455566677778889
./.

(?<=(\d)(\w#?){9}).#|.#(?=(\w#?){9}(\d)(?!#))
$1$4
#

_(?=.{9}(.))|(?<=(.).{9})_
$1$2
^(\d*)\1$|.*
$1

オンラインでお試しください!

説明:

最初の行?は、入力内の#すべてとすべての文字を同等の数値に変換します。次に、スペースと/入力を削除します。次の2行は、「推測vs確実性」のケースを処理します(例えば、5? \ 4に置き換えられます4 \ 4)。すべて#のsを削除した後、8行目と9行目は「数値vs._」のケースを処理します(に_ \ 3なります3 \ 3)。次に、両方の文字列が一致する場合、最初の10桁を保持します。それ以外の場合、電話番号は無効であるため、すべて削除します。

任意の長さ(および等しいサイズ)の電話番号で機能する代替160バイトソリューション:TIO


toを変更し(/|_)[/_]1バイトを節約できます。また、私はあなたが使用することができると思う;の代わりに、xそれはよう[^x]になることができます\w
KritixiのLithos

1

PHP、 251 236バイト

for(;a&$c=preg_replace(["#[^_?](?!\?)#","#_#"],["$0k","?<"],join("-",$argv))[++$i];)${$k+="-"==$c}.=$c<_&$c>=A?0|(ord($c)-($c>W)-($c>P)-59)/3:$c;for(;$c=${1}[$k+1];)echo($n=${1}[$k])==($m=${2}[$k++])|($b=${2}[$k++])!=$c?$c>$b?$n:$m:"?";

コマンドラインから入力を受け取ります。と走る-nr、オンラインで試してください

壊す

# A: transform input
                                    # 2. replace single chars with two-character chunk and make sortable:
                                    #   replace "_" with "?<", append "k" to everything else not followed by "?"
for(;a&$c=preg_replace(["#[^_?](?!\?)#","#_#"],["$0k","?<"],join("-",$argv))[++$i];)    # (unknown "<" < unsure "?" < certain "k")
${$k+="-"==$c}.=                # if "-", next argument
        $c<_&$c>=A              # if letter
            ?0|(ord($c)-($c>W)-($c>P)-59)/3 # then translate to digit
            :$c                             # else don´t
    ;
# B: evaluate
for(;$c=${1}[$k+1];)            # loop through arguments: $c=command 2
    echo
        ($n=${1}[$k])                   # $n=digit 2
        ==                          # if digits are equal
        ($m=${2}[$k++])                 # $m=digit 3
        |
        ($b=${2}[$k++])             # $b=command 3
        !=$c                        # or "commands" are not
            ?$c>$b?$n:$m            # then get the one with the more definitive "command"
            :"?"                    # else conflict/unknown
    ;

ゴルフ

  • preg_replace 最初:-8バイト
  • join:-2
  • $$k代わりに$t[$k]:-5

1

PHP、200 + 8バイト

Arnauldsソリューションに触発されました

for($s=join($argv);$c=ord($s[$i++]);$i+=$x)$t[]=$c>90?63:15&($c<65?$c:($c-($c>80)-($c>87)-59)/3)|16*$x="?"==$s[$i];for(;$p++<10;)echo chr(($e=$t[$p]^$d=$t[$p+10])&48|!(15&$e)?min($t[$p],$d)&15|48:63);

コマンドライン引数から入力を受け取ります。で実行する-nr、オンラインで試してください

エラー出力制限に準拠するための変更:(printX不完全な番号の):

  • 取り除く |48(-3バイト)
  • 置き換えるecho chr(...);$r.=...;echo$r>1e10?X:$r;(11バイト)

壊す

for($s=join($argv);$c=ord($s[$i++]);    # loop through characters of arguments
    $i+=$x)                             # skip "?"
$t[]=
    $c>90                               # if "_"
        ?63                             # then 32+16+15
        :                               # else
            15&(                            # lower 4 bits of
            $c<65                               # if digit
            ?$c                                 # then digit
            :($c-($c>80)-($c>87)-59)/3          # else letter mapped to digit
        )
        |16*$x="?"==$s[$i]                  # if next char is "?", add 16
;
for(;$p++<10;)echo chr( # loop through translated arguments
    (
        $e=$t[$p]^      # 2. $e=difference
        $d=$t[$p+10]    # 1. $d=char from 2nd argument
    )&48                # if certainties differ
    |!(15&$e)           #    or digits do not
    ?min($t[$p],$d)&15|48   # then pick the more definite digit (15|48 -> "?")
    :63             # else "?"
);

ゴルフ

  • 回避する preg_replace_callback策(-10バイト)
  • 10桁の入力に依存(-9)
  • および追加のゴルフ(-8)
  • 削除された joinデリミタを(-7)
  • $x割り当てを最後に移動しました(-2)

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.