私の疑似コードを現実のものにする


8

私は、用途は中括弧の代わりに空白といういくつかのJavaの擬似コードを持っている、と私はしたい、あなたがそれを変換します。

I / O

プログラムは、ブロックをインデントするために使用されるスペースの数を指定する番号とともに、入力ファイルを取得する必要があります。次に例を示します。

$ convert.lang input.p 4
// 4つのスペースをブロック区切り文字として使用して変換します
$ convert.lang input.p 2
// 2つのスペースをブロック区切り文字として使用して変換します

次に、指定されたブロック区切り文字を使用して結果を変換し、結果をstdoutに出力します。

プログラムの要点

ブロックはで開き:、ブロック内の各行は、Pythonコードのようにブロック区切り文字を使用してインデントされます。

while(true):
    System.out.println( "Test");

各々が:で置換され{、そして}ブロックの末尾に追加されます。

while(true){
    System.out.println( "Test");
}

入力:

パブリッククラステスト:
    public static void main(String [] args):
        System.out.println( "Java is verbose ...");

出力:

$ Test.pseudojava 4を変換します
パブリッククラスTest {
    public static void main(String [] args){
        System.out.println( "Java is verbose ...");
    }
}

入力:

メイン():
  printf( "Hello World");

出力:

$ test.file 2を変換
main(){
  printf( "Hello World");
}

入力:

def generic_op(the_stack、func):
    #一般的な操作コード
    b = the_stack.pop()
    isinstance(b、list)の場合:
        もしb:
            返す
        トップ= b.pop(0)
        一方、b:
            top = func(top、b.pop(0))
        the_stack.push(トップ)
    そうしないと:
        a = the_stack.pop()
        func(a、b)を返す

出力:

$ code.py 4を変換
def generic_op(the_stack、func){
    #一般的な操作コード
    b = the_stack.pop()
    isinstance(b、list){
        もしb {
            返す
        }
        トップ= b.pop(0)
        一方、b {
            top = func(top、b.pop(0))
        }
        the_stack.push(トップ)
    }
    そうしないと {
        a = the_stack.pop()
        func(a、b)を返す
    }
}

得点

バイト数が最も少ないコードが優先されます


1
入力にコメントが含まれていないと想定できますか?
マーティンエンダー

1
@MartinBüttnerコメントが含まれる場合がありますが、コメントには「:」は含まれません。基本的にそうです。
フェーズ

3
有効なJavaソースで行がコロンで終わる通常の理由であるラベルについてはどうですか?
Peter Taylor

1
ラベルは行の始め以外には見たことがありません。
SuperJedi224 2015年

2
Javaがいかに嫌いかを思い出しました。
リルトシアスト2015年

回答:


5

Perl、41バイト

#!perl -p0
1while s/( *).*\K:((
\1 .*)+)/ {\2
\1}/

シバンを2として数え、入力はstdinから取得されます。コマンドライン引数を指定する必要はありません。インデントのサイズを知らなくても、有効なネストコンテキストを決定(および照合)できます。


正規表現の内訳

( *)                   # as many spaces as possible (\1)
    .*                 # as many non-newline characters as possible \
                         (greediness ensures this will always match a full line)
      \K               # keep all that (i.e. look-behind assertion)
        :              # colon at eol (newline must be matched next)
         (
          (
           \n\1        # newline with at least one more space than the first match
                .*     # non-newlines until eol
                  )+   # as many of these lines as possible
                    )  # grouping (\2)

使用例

in1.dat

public class Test:
    public static void main(String[] args):
        System.out.println("Java is verbose...");

出力

$ perl py2java.pl < in1.dat
public class Test {
    public static void main(String[] args) {
        System.out.println("Java is verbose...");
    }
}

in2.dat

main():
  printf("Hello World");

出力

$ perl py2java.pl < in2.dat
main() {
  printf("Hello World");
}

in3.dat

def generic_op(the_stack, func):
    # Generic op handling code
    b = the_stack.pop()
    if isinstance(b, list):
        if b:
            return
        top = b.pop(0)
        while b:
            top = func(top, b.pop(0))
        the_stack.push(top)
    else:
        a = the_stack.pop()
        return func(a, b)

出力

$ perl py2java.pl < in3.dat
def generic_op(the_stack, func) {
    # Generic op handling code
    b = the_stack.pop()
    if isinstance(b, list) {
        if b {
            return
        }
        top = b.pop(0)
        while b {
            top = func(top, b.pop(0))
        }
        the_stack.push(top)
    }
    else {
        a = the_stack.pop()
        return func(a, b)
    }
}

私はこれをルビーで書いた
だけです

2

Python 3、299 265バイト

import sys;s=int(sys.argv[2]);t="";b=0
for l in open(sys.argv[1]):
 h=l;g=0
 for c in l:
  if c!=" ":break
  g+=1
 if g/s<b:h=" "*g+"}\n"+h;b-=1
 if l.strip().endswith(":"):h=l.split(":")[0];h+=" {";b+=1
 t+=h+"\n"
b-=1
while b>-1:
 t+=" "*(b*s)+"}\n"b-=1
print(t)

ブームバムパウ。

使用されるアルゴリズム:

//グローバル変数
string total //変更されたプログラムの合計
int b //インデントバッファ

line through through lines://すべての行を繰り返す
  string mline = "" //合計に追加される行

  //行の前のスペースの量を計算します(はるかに簡単になります)
  int space = 0 //合計スペース
  c thru line://行のすべての文字を通過します
    if c!= ""://現在の文字がスペースでない場合(つまり、すべての文字を処理した
        break // charの反復処理から抜け出す
    スペース++ //スペースに当たったのでスペースをインクリメントする(hur derr)

  スペース/ SPACE_SETTING <bの場合://現在の行のインデント数がインデントバッファーより小さい場合
    mline = "} \ n" + line //行の始めに閉じ括弧を追加
    b-- //デクリメントバッファ

  if line.endswith( ":")://行が `:`で終わる場合
    削除:行から
    mline + = "{" //追加{
    b ++ //増分バッファ
  合計+ = mline //変更された行を合計に追加

印刷(合計)

説明を含めることはできますか?
TanMath 2015年

@TanMathは、私が使用したアルゴリズムを追加しました
フェーズ

Python 2で動作しますか?
wb9688 2015年

@ wb9688わからない、私はそれをPython 3でテストしただけ
フェーズ

私はテストしたばかりで、Python 2で動作します
wb9688 2015年

2

ルビー、70歳

x=$_+"
"
1while x.sub! /^(( *).*):
((\2 .*?
)*)/,'\1 {
\3\2}
'
$><<x

末尾に改行を追加します。インデントブロックサイズパラメータは必要ありません。

これを実行します-n0(これは実際には68 + 2です)。1ダース以上のバイトを節約してくれた@primoに感謝します。


-p0rubyでも機能すると思います(-0すべての入力を一度に読み取り、-pstdinを$_に格納し、最後に自動印刷します)。
primo

@primo良い点。場合には、それは上記の私のコメントで明確ではなかった、これはあなたのコードのポートではなく、あなたが行うまさにん私自身の仕事(ただし、以上のバイトで)
未ことチャールズ・

私は正しく理解しましたx=$<.readlines*''。(かなり冗長)を削除するためのヒントを提供するだけです。私がそれをしている間sub!、置換文字列を受け入れる2つのパラメーターのオーバーロード(1つのパラメーター+ブロックではなく)もあるので\1\2すべてを連結する必要がない代わりに、、などを使用できます。
プリモ2015年

@primoありがとう!以前に2パラメータバージョンを試してみて、昨夜のある時点でそれを放棄しました。
それはチャールズではない
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.