質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.31%
Java

Javaは、1995年にサン・マイクロシステムズが開発したプログラミング言語です。表記法はC言語に似ていますが、既存のプログラミング言語の短所を踏まえていちから設計されており、最初からオブジェクト指向性を備えてデザインされています。セキュリティ面が強力であることや、ネットワーク環境での利用に向いていることが特徴です。Javaで作られたソフトウェアは基本的にいかなるプラットフォームでも作動します。

Eclipse

Eclipseは、IBM社で開発された統合開発環境のひとつです。2001年11月にオープンソース化されました。 たくさんのプラグインがあり自由に機能を追加をすることができるため、開発ツールにおける共通プラットフォームとして位置づけられています。 Eclipse自体は、Javaで実装されています。

Q&A

解決済

2回答

1717閲覧

(Eclipse)ファイルからの標準入力を受けるとき、EOFを取得する方法

toot_iba

総合スコア10

Java

Javaは、1995年にサン・マイクロシステムズが開発したプログラミング言語です。表記法はC言語に似ていますが、既存のプログラミング言語の短所を踏まえていちから設計されており、最初からオブジェクト指向性を備えてデザインされています。セキュリティ面が強力であることや、ネットワーク環境での利用に向いていることが特徴です。Javaで作られたソフトウェアは基本的にいかなるプラットフォームでも作動します。

Eclipse

Eclipseは、IBM社で開発された統合開発環境のひとつです。2001年11月にオープンソース化されました。 たくさんのプラグインがあり自由に機能を追加をすることができるため、開発ツールにおける共通プラットフォームとして位置づけられています。 Eclipse自体は、Javaで実装されています。

1グッド

0クリップ

投稿2023/06/18 23:27

編集2023/06/19 05:01

実現したいこと・知りたいこと

  • Eclipseでデバッグをする際に、標準入力を入力ファイルとして受け取り、そのままEOFまで取得したい
  • 発生している現象は、他の方の環境で再現性があるのかどうか

前提

Eclipseにて標準入力を受けるプログラムをJavaで作成しています。デバッグにあたり、標準入力を事前に作成したファイルから与えられると便利です。

eclipseの機能として、標準入力をファイルから流す機能はあるようです。
デバッグボタンの隣の▼ボタン > デバッグの構成 > 共通タブ > 標準入出力 > コンソールに割り当てと入力ファイル にチェック
標準入出力の設定箇所

この方法を試したところ、後述のコードのscanner.nextLine();にてプログラムは止まるようになりました。
想像するに、EOFを受け取ることができず、待機状態となっているものと思います。

コンソールからの入力であれば、正常にscanner.close()へ遷移します。
上記のEclipseの設定にて、標準入出力をコンソールと入力ファイルの両方から入力を受け付けるようにし、scanner.nextLine()での待機中にコンソールからCtrl-Dを押すと、正常にscanner.close()へ遷移します。このとき、入力ファイルの内容がscannerによって読み取られていることを確認しています。ただこの回避策は不便ですので、わざわざコンソールで操作しなくとも、入力ファイルから標準入力を受け取り、処理が進んでほしいと思っています。

該当のソースコード

プログラムは次の通りです。

java

1package sample; 2 3import java.util.Scanner; 4 5public class Sample { 6 7 public static void main(String[] args) { 8 Scanner scanner = new Scanner(System.in); 9 String input = scanner.nextLine(); 10 scanner.close(); 11 12 System.out.println(input); 13 } 14}

標準入力としては画像のようにファイルを指定しています。ファイル内容は次のとおりです。

text

1Hello World!

補足情報(FW/ツールのバージョンなど)

  • Ubuntu 20.04.6
  • Eclipse 2023-03 (4.27.0)
  • Java openjdk version "11.0.19" 2023-04-18
jimbe👍を押しています

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

jimbe

2023/06/19 04:28 編集

入力ファイルに指定したファイルの中身はどうなっているのでしょうか。 >コンソールと入力ファイルの両方から入力を受け付けるようにし とはどういうことでしょう。 リダイレクト(やパイプ)しているなら、ご提示のコードでは片方しか受け付けないはずですが。 プログラムに問題がある可能性がある場合は、プログラムのご提示時は省略等は極力しないようにしてください。 省略した部分もしくは省略した部分との関係によって問題がある可能性があります。 eclipse の設定に関しましても、設定のスクリーンショットを載せて頂く等すると、勘違いや設定不足等があれば何方かが気が付くかもしれません。
toot_iba

2023/06/19 05:10

コメントいただきありがとうございます。 > >コンソールと入力ファイルの両方から入力を受け付けるようにし > とはどういうことでしょう。 > リダイレクト(やパイプ)しているなら、ご提示のコードでは片方しか受け付けないはずですが。 これは、Eclipseの設定を説明していました。 確かにわかりにくいと感じたため、質問に画像を追加しました。 Eclipseのプロジェクトを開いた状態で、次のように設定をたどっていきます。 `デバッグボタンの隣の▼ボタン > デバッグの構成 > 共通タブ > 標準入出力 > コンソールに割り当てと入力ファイル にチェック` 最後に、標準入力として、何を入れるか、というチェックボックスがあります。 そのチェックボックスについて、「コンソールと、入力ファイルの両方にチェックした」という意味です。 ご指摘を受け、一つ気が付きました。 通常のコマンド実行において、リダイレクトを使うことを思い出すと 通常は、標準入力は、端末から受けるか、ファイルから受けるかの2つに1つです。(ご指摘の通り) Eclipseに両方を指定できるということは、リダイレクトの代わりが実装されているわけではないということです。 例えば、この機能はあくまで、標準入力にファイルの内容を貼り付けるに過ぎないのかもしれません。 そうであれば、EOFを受け付けないことに納得できます。 Eclipseの設定で実現する方法はなさそうだと思いました。 他の方法として、実装を変えたり、mavenやmakefileなどを利用して実現する方法を探したり、そもそもコマンド実行としてしまうなどを検討したく思います。 とりあえず質問としてはeclipseでの方法を探していたため、解決といたします。 ありがとうございました。
jimbe

2023/06/19 05:34 編集

編集ありがとうございます。 一応解決にするとのことですが、1つ確認させてください。 input.txt の行の最後に改行は入っていますでしょうか。
toot_iba

2023/06/19 05:51 編集

input.txtの行の最後に改行は入っていませんでした。 改行を入れて実行したところ、適切にプログラムが進行することがわかりました。 こちらのほうが望ましい解決です。ありがとうございます。 改行あり/なしについては試していたのですが、試行錯誤の中で、成功パターンが漏れていました。 改行あり かつ 「コンソール + 入力ファイル指定の設定」(質問に添付の画像の設定) の場合に、動作します。 改行あり かつ 「入力ファイル指定の設定」では、動作しませんでした。 簡単で構いませんので解決策として回答いただけないでしょうか。ベストアンサーをそちらに差し替えます。
jimbe

2023/06/19 06:19 編集

改行の有無で動作が変わるのは Eclipse 上での動作だけで、実際のコンソール上等で実行した場合は改行が無くても問題が無いのではないでしょうか。 そういう意味では Eclipse の環境がホンモノと違うのは確かで、回答に書かれた内容は間違っていないように思います。 改行を入れて動作させるというのは回答に書かれた「入力を受け付ける仕組みをEOFに依らないものに変更」と同じこととも考えられます。
xebme

2023/06/19 09:38

Scanner.hasNext()でわかりませんか。 標準入力は文脈に依存します。閉じるとプログラムから開けません。
xebme

2023/06/19 09:45

EOF文字は取得できません。
xebme

2023/06/21 01:32

何を質問したいのかわかりません。ファイルに複数行格納されていても1行しか読まないのが問題ならロジックが悪い。for/whileを学習してください。
toot_iba

2023/06/21 09:47

@jimbe 様 コンソール上で実行した場合の確認はできませんでした。(私の技術的な問題ですぐには実行確認できませんでした) 想像するところでは、コンソール上で、リダイレクトによりファイルから標準入力を与えれば、EOFが受け取られ、`scanner.nextLine()`は終了しそうだと思っています。 少なからず誤解して書いていたという認識は変わりません。`scanner.nextLine()`がEOFによってのみ終了するものだという前提で書いていました。 コメントに対するせめてものお礼をしたかったなというお気持ちで、回答の記載をお願いしていました。が、強要するものではありませんから、こちらで回答記載させていただきます。 ありがとうございました。
toot_iba

2023/06/21 09:48

@xebme 様 コメントいただきありがとうございます。 > Scanner.hasNext()でわかりませんか。 > 標準入力は文脈に依存します。閉じるとプログラムから開けません。 > EOF文字は取得できません。 > 何を質問したいのかわかりません。ファイルに複数行格納されていても1行しか読まないのが問題ならロジックが悪い。for/whileを学習してください。 コメントの意味を想像するに、`Scanner.hasNext()`の用途と考えれば疑問が解消するのでは?という示唆かと思います。 実際、私に誤解がありました。`Scanner.nextLine()`がEOFによって"のみ"読み取りを終了するはずだという思い込みです。 `Scanner.hasNext()`を使った、EOFまで読み込むような処理を提示していれば、質問内容が通りやすかったかもしれません。失礼いたしました。 また、EOFの役割を担う文字を取得したいという質問ではありませんでした。
guest

回答2

0

Eclipseでデバッグをする際に、標準入力を入力ファイルとして受け取り、そのままEOFまで取得したい

これをEclipseの機能として実現する方法はないと思われます。Eclipseの標準入力としてファイルを与える機能はリダイレクトとは異なり、EOFを発行しない仕組みのようです。これはコンソールからの入力と入力ファイルからの入力が共存していることからわかります。(そういった利便性ももたらしています)

入力を受け付ける仕組みをEOFに依らないものに変更するか、Eclipseからのデバッグをあきらめ、コンパイル後、CUIからリダイレクトで入力ファイルを流す方法が有力です。

Eclipseの機能として解決することを期待していましたが、そういった機能ではなさそうであることに納得できましたのでクローズといたします。

誤解がありましたので取り消します

投稿2023/06/19 05:20

編集2023/06/19 05:51
toot_iba

総合スコア10

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

0

自己解決

Eclipseの標準入出力の設定について

質問内容に載せている、標準入力の設定について、どのような機能であるのかを観察します。

コンソールを割り当て入力ファイルの指定の両方を指定している場合、これはシェルのリダイレクトとは異なる性質であることが想像されます。コンソールとファイルの異なる2つのストリームを扱っているように見えるためです。

そしてどうやら、指定した入力ファイル終端において、EOFを返さないらしいということがわかっています。
例えば、ファイルの内容をコンソールに貼り付けるような実装となっているのかもしれません。Eclipseのソースを確認すればよいのかもしれませんが、そこまでは労力をかけていられませんので割愛します。

代替策

意図していた動作を実現するための代替策を考えます。
質問のソースコードを前提に、代替策として望ましいものは、入力ファイルの最後に改行を入れるというものです。
これにより、標準入力を処理するString input = scanner.nextLine();は終了し、scanner.close();へ進行します。

そもそも、scanner.nextLine()は文字通り、入力を一行進めて、進めた文の一行を得る処理です。
EOFによって処理は終了するかもしれませんが、それが必要条件というわけではありません。改行によっても終了します。
(ここを質問時に誤認していたため、質問内容がよくわからないものと思われたのではないでしょうか。失礼いたしました)

質問中の入力処理では、標準入力から1行受け取る処理を書いていましたが、
複数行を受け取りEOFで終了するような処理の場合は、例えばコンソールからCtrl+Dを入力してやる必要があるようです。

java

1while (scanner.hasNext()) { 2 String line = scanner.nextLine(); 3 inputBuilder.append(line); 4 inputBuilder.append(System.lineSeparator()); 5} 6scanner.close();

Eclipseの機能では、入力ファイルの終端でEOFを認識させられないようです。

その他にも、特定の文字列を受け取り終了するなど別の方法によって代替することもできるでしょう。

投稿2023/06/21 09:15

編集2023/06/21 11:09
toot_iba

総合スコア10

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

xebme

2023/06/21 10:35

標準入力の対象がコンソールから打ち込まれたものなのか、ファイルから読み込まれたものなのかは、プログラムで判断できません。したがってhsNext()で入力の終了を判断するしかありません。 UbuntuのCTL+Dは、WindowsではCTL+Z+returnになります。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.31%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問