2012-05-09 9 views
3

私はあなたの提案と指導が必要です。 私はlibdmtxを使用しています。コマンドラインユーティリティには、ECC200 Data Matrixバーコードのイメージファイルを読み込み、その内容を読み込み、デコードされたメッセージを標準出力に書き出します。 私はこのコマンドラインユーティリティをLinuxプラットフォーム上の私のJavaプログラムで使いたいと思っています。私はubuntu linuxを使っています。 Linuxマシンにlibdmtxをインストールしました。私はLinuxの端末にJavaプログラムから呼び出されたときにコマンドラインユーティリティがハングするのはなぜですか?

/home/admin/ab.tif

dmtxread -nコマンドを実行するとき、それはすぐに、画像内のバーコードのデコード値を与えます。

私のjavaプログラムを使用してこのコマンドを呼び出すとき、コマンドの実行中にstuksコードが出力され、出力が得られます。 プログラムが処理中またはハングアップしているように見えます。続き

は私に私のコードが間違って起こっている友人を教えてください、次のコマンド

import java.io.BufferedReader; 
import java.io.File; 
import java.io.IOException; 
import java.io.InputStreamReader; 


public class Classtest { 

    public static void getCodes(){ 

     try 
     { 
      Process p; 
      String command[]=new String[3]; 
      command[0]="dmtxread"; 
      command[1]="-n"; 
      command[2]="/home/admin/ab.tif"; 

      System.out.println("Command : "+command[0]+command[1]+command[2]); 
      p=Runtime.getRuntime().exec(command); //I think hangs over here. 

      BufferedReader reader=new BufferedReader(new InputStreamReader(p.getErrorStream())); 
      String line=reader.readLine(); 
      if(line==null){ 
       reader=new BufferedReader(new InputStreamReader(p.getInputStream())); 
       line=reader.readLine(); 
       System.out.print("Decoded  :- "+line); 
      }else{ 
       System.out.print("Error  :- "+line); 
      } 
      System.out.println(p.waitFor()); 

     }catch(IOException e1) { 
      e1.getMessage(); 
      e1.printStackTrace(); 
     }catch(InterruptedException e2) { 
      e2.getMessage(); 
      e2.printStackTrace(); 
     } 


    } 
    public static void main(String args[]){ 
     getCodes(); 
    } 

} 

を呼び出し、私のJavaコードです。

私は任意のヘルプ

http://www.javaworld.com/javaworld/jw-12-2000/jw-1229-traps.html?page=1

を得る私の友人を案内してください、次の資料が、くぼみに参照さ! ありがとうございました!

このコードはProcessBuilderクラスを使用したこのコードで、このコードは上記のコードと同じ出力を与えています。これは、行でハングするコードです Process process = pb.start();

public class Test { 

public static void main(final String[] args) throws IOException, InterruptedException { 
    //Build command 
    List<String> commands = new ArrayList<String>(); 
    commands.add("dmtxread"); 
    commands.add("-n"); 
    commands.add("/home/admin/ab.tif"); 
    System.out.println(commands); 

    //Run macro on target 
    ProcessBuilder pb = new ProcessBuilder(commands); 
    pb.redirectErrorStream(true); 
    Process process = pb.start(); 

    //Read output 
    StringBuilder out = new StringBuilder(); 
    BufferedReader br = new BufferedReader(new InputStreamReader(process.getInputStream())); 
    String line = null, previous = null; 
    while ((line = br.readLine()) != null){ 
     System.out.println(line); 
    } 

    //Check result 
    if (process.waitFor() == 0) 
     System.out.println("Success!"); 
    System.exit(0); 

    //Abnormal termination: Log command parameters and output and throw  ExecutionException 
    System.err.println(commands); 
    System.err.println(out.toString()); 
    System.exit(1); 
} 

}

この問題を解決するために私を導いてください。 ありがとうございました!

答えて

0

は、私は正確にあなたのプログラムで何が起こるかわからない、それがハングしない場所(デバッガを使用することができますか、それを確認するために、出力をトレース)が、ここで考えられるシナリオです:プログラムがしようとする場合を想定し

2行のテキストを出力します。または1行だけが標準エラーになります。あなたのコードはの1行だけとなり、プロセスが終了するのを待つよりも遅くなります。これは、子プログラムが読者が次の行を読むのを待つことを意味するので、誰かがパイプのブロックを永久に解除するまで、writeで待機します。

コマンドラインからdmtxreadを実行すると、出力パイプでブロックされないので、プログラムは細かく実行されます。

+0

ありがとうございました返信ありがとうございました!あなたが示唆したように私はコードをチェックしますが、エラーも出力もしません。 –

+0

@ Param-Ganak:おそらく 'reader.readLine()'はプログラムが何かを出力するのを待っていますか? – Vlad

+0

私は本当にどこにプログラムが間違っているのかわかりません。私は、コマンドが最初のコードで実行されるとき、プログラムはアプリケーションからの応答を待っていることを確信しています。 –

2

あなたのストリーム消費コードは非常に混乱しています。 stderrから一行を読み込み、その読み手を放棄して、stdoutから一行を読み込もうとします。

  1. プログラムは、プログラム自体が意志、それはそのバッファを埋めるように、プログラムはstderrにすぎのものを送信した場合は、2行目
  2. でハングアップするでしょう、stderrには何も印刷されない場合あなたのJavaはブロックされますwaitFor
  3. これらはどちらもstdoutに適用されます。

プロセスの出力ストリームを適切に使用する方法については、リンクしている記事を参照してください。そのアドバイスを受けて、誰もあなたより良いアドバイスを与えることはできません。

+0

お返事ありがとうございました!あなたが提案したように私はリファレンスリンクごとに自分のコードに変更を加えましたが、著者が記事の4ページ目に追加したstreamgobblerクラスを追加してプログラムを実行しようとしましたが、System.out.println ( "コマンド:"); line –

+0

あなたが掲示したコードから、どの行のコードブロックがどのように結論付けられたのかは明らかではありません。あなたのコードがその特定の行で本当にブロックされているという説得力のある議論をしてください。 –

+0

私の質問で2番目のコードを実行すると、最初のコードと同じように動作しましたが、非常に長い時間が経過した後、出力が得られましたが、問題はコードが1つの画像でバーコードをスキャンするために要した時間です。 –

4

readLineは、エラーストリームから新しい行を受け取るまでブロックします。したがって、出力がない場合、プログラムは最初のreadLineを通過しません。簡単にするために

私はあなたが以下のように使用すると、2つの、入力ストリームをマージすることができますProcessBuilderの代わりRuntime.exec()、使用をお勧めします:

ProcessBuilder builder = new ProcessBuilder(cmd,arg0,arg1); 
builder.redirectErrorStream(true); 
Process process = builder.start(); 

をだから今、あなただけの1から読み取ることができますが、。

また、別のスレッドを使用して2つのInputStreamを使用することもできます。

希望のある方

+0

お返事ありがとうございます。私のコードであなたが提案した変更を行い、その結果をお知らせします。 –

+0

上記の解決方法を実装したボトムの私の質問に追加したコードを確認してください。 –

+0

ええと、今は大丈夫です。試してみるべきことがいくつかあります:1)あなたのプログラムを使って 'ls'のようなコマンドを実行してください。すべての出力? 2) 'while'ブロック全体をコメントアウトして、waitForに到達するかどうかを確認します。 3)デバッガをステップスルーして、どれだけ距離があるかを知ることができます(または各行の間に何かを印刷するだけです) – laher

関連する問題