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

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

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

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

Android

Androidは、Google社が開発したスマートフォンやタブレットなど携帯端末向けのプラットフォームです。 カーネル・ミドルウェア・ユーザーインターフェイス・ウェブブラウザ・電話帳などのアプリケーションやソフトウェアをひとつにまとめて構成。 カーネル・ライブラリ・ランタイムはほとんどがC言語/C++、アプリケーションなどはJavaSEのサブセットとAndroid環境で書かれています。

Android Studio

Android Studioは、 Google社によって開発された、 Androidのネイティブアプリケーション開発に特化した統合開発ツールです。

Q&A

解決済

1回答

1375閲覧

BufferedReader readerに読み込めれない。

eisaku123

総合スコア74

Java

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

Android

Androidは、Google社が開発したスマートフォンやタブレットなど携帯端末向けのプラットフォームです。 カーネル・ミドルウェア・ユーザーインターフェイス・ウェブブラウザ・電話帳などのアプリケーションやソフトウェアをひとつにまとめて構成。 カーネル・ライブラリ・ランタイムはほとんどがC言語/C++、アプリケーションなどはJavaSEのサブセットとAndroid環境で書かれています。

Android Studio

Android Studioは、 Google社によって開発された、 Androidのネイティブアプリケーション開発に特化した統合開発ツールです。

0グッド

0クリップ

投稿2018/03/03 02:56

編集2018/03/03 09:32

いつもお世話になります。

下図のように3行追加するとBufferedReader readerに読み込むことができなくなくなります。
disconnect()にしてもうまくいかないです。

何が問題あるのでしょう?

java

1//①クライント側 アンドロイドアプリ 2@Override 3 protected Result doInBackground(Void... voids) { 4 5 Result result = new Result(); 6 7 8 9 byte[] data; 10 result.bitmap = null; 11 result.text=null; 12 13 InputStream inputStream = null; 14 15 StringBuilder builder = new StringBuilder(); 16 try { 17 URL url = new URL("http://192.168.3.5:8080/book123/chapter14/search"); 18 HttpURLConnection con = (HttpURLConnection)url.openConnection(); 19 20 //↓↓↓↓↓↓↓↓↓ここ3行追加すると BufferedReader readerに読み込めない 21 con.connect(); 22 inputStream = con.getInputStream(); 23 result.bitmap = BitmapFactory.decodeStream(inputStream); 24       //↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑↑ 25 26       //↓↓↓↓↓↓読み込めれない 27 BufferedReader reader = new BufferedReader(new InputStreamReader(con.getInputStream(), "UTF-8")); 28 String line; 29 while ((line = reader.readLine()) != null){ 30 builder.append(line); 31 } 32 33 result.text = builder.toString(); 34 35 }catch (IOException exception){ 36 37 } 38 return result; 39 } 40 41 @Override 42 protected void onPostExecute(Result result) { 43 44 imageview.setImageBitmap(result.bitmap); 45 textView.setText(result.text); 46 47 } 48 49}

java

1//②サーバー側 2public class Hello extends HttpServlet{ 3 4 @Override 5 public void doGet( 6 HttpServletRequest request, 7 HttpServletResponse response 8 ) throws ServletException, IOException { 9 10 try { 11 response.setContentType("application/octet-stream ;charset=UTF-8"); 12 response.setHeader("Content-Disposition" ,"attachment"); 13 14 OutputStream out = response.getOutputStream();//画像側のストリーム<===エラー:getOutputStream()はこのレスポンスに対して既に呼び出されています 15 16       //////テキスト////////start///////////////////////////////// 17 PrintWriter out2=response.getWriter();//テキスト側のストリーム 18 out2.println("こんにちは777777"); 19 //////テキスト////////end///////////////////////////////// 20 21 22 //////画像側////////start///////////////////////////////// 23 FileInputStream input =new FileInputStream("/Applications/Eclipse_4.7.2.app/Contents/workspace/.metadata/.plugins/org.eclipse.wst.server.core/tmp0/wtpwebapps/book777/WEB-INF/classes/chapter3/1.jpg"); 24 25 int i = input.read(); 26 while(i !=-1) { 27 char c = (char)i; 28 out.write(c); //ここでバイナリーデータを流している 29 i = input.read(); 30 } 31 input.close(); 32 out.close(); 33 34 //////画像側////////end///////////////////////////////// 35 36 }catch(Exception e) { 37 System.out.println("意味不明のエラーです"); 38 System.out.println(e); 39 }catch (Throwable e) { 40 System.out.println("byte[] data = IOUtils.toByteArray(input);でエラーです"); 41 } 42 43 //out.close(); 44 } 45 46}

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

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

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

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

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

退会済みユーザー

退会済みユーザー

2018/03/03 03:01 編集

例外ないんでしらんが BitmapFactory.decodeStream がクローズしてんじゃね(どのパッケージのか、独自実装かもらんし)
退会済みユーザー

退会済みユーザー

2018/03/03 03:06

あと InputStream 内でポインタをもどしてるのかしら(HTTPconnectionのなら戻せないはずだが)
eisaku123

2018/03/03 04:52

BitmapFactory.decodeStream のみをコメントアウトする読み込めれますね。ただしこれも画像の処理として生かしたいです。
ngsvx

2018/03/03 08:11

よくわからないけど、このURLのものって、画像とテキストがくっついているということ?
eisaku123

2018/03/03 08:32

画像はくっついてないです。しかしサーバー側からバイナリーの画像データが送られきます。
ngsvx

2018/03/03 08:36

いやいや、だってこのコードを見ると、最初に画像を受信して、そのまま同じストリームでテキストを受信してるでしょ?ということは、画像とテキストがくっついた1つのファイルを受信するということになるでしょ?
eisaku123

2018/03/03 09:31

くっついていない状態です。サーバー側を追記しました。こんな感じです。(エラーは出るけど)
退会済みユーザー

退会済みユーザー

2018/03/03 11:21

HTMLと同時に画像を送る方法は <img src='data:image/png;base64,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'> のような方式しかないですよ
eisaku123

2018/03/03 12:08

このやり方はngsvxさんの1つめの方法でしょうか? base64 と記載されているため
退会済みユーザー

退会済みユーザー

2018/03/03 12:19

base64 といってるとこのですね。
退会済みユーザー

退会済みユーザー

2018/03/03 12:32

ちなみに chunk は データを返す方式じゃなくレスポンスを分割しますよ(マルチパートレスポンス)
退会済みユーザー

退会済みユーザー

2018/03/03 12:33

可変長(固定長)データ形式は すべてバイナリで返却してます。(何らかのふた手間が必要)
guest

回答1

0

ベストアンサー

長くなりそうなので、こっちに書きます。

サーバー側で例外が発生していませんか?

apiドキュメントを見ると、response#getWriterは、

このメソッドか getOutputStream() メソッドのどちらかをボディメッセージの出力に使用します。両方は使えません。

例外
java.lang.IllegalStateException - このレスポンスオブジェクトの getOutputStream メソッドがすでに実行されていた場合

とあります。

ですので、

PrintWriter out2=response.getWriter();//

の行で例外が発生しているのではないかと推測します。

仮に例外が発生しない仕様だったとしても、基本的な考え違いがあると思います。

1つのコネクションでは、入力ストリームと出力ストリームはそれぞれ各1つで、計2つしかありません。

もし、getWriterで例外が発生しないとしても、getWriterとgetOutputStreamは同じストリームを使います。

従って、受信側(クライアント側)からすると、画像ファイルとテキストは、1つのファイルとして認識されます。

そのため、送信側で2つのデータがあるということ

投稿2018/03/03 10:07

ngsvx

総合スコア287

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

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

eisaku123

2018/03/03 10:49

サーバー側で java.lang.IllegalStateException: getOutputStream()はこのレスポンスに対して既に呼び出されています つまり一回のコネクションでgetWriterかgetOutputStreamのどちらしか選択できないということですね。 またクライアント側ではgetInputStreamを2回使っているので2回目は空っぽか、使えない、というふうに繋がりますね。 ではファイルと画像を同時にレスポンスし、クライアント側で、画像とファイルを選別してImageViewとTextViewに表示できる方法ってあるのでしょうか?
ngsvx

2018/03/03 10:59

>ではファイルと画像を同時にレスポンスし、 1つのコネクションでテキストファイルと画像を送受信するといういみでしょうか?
eisaku123

2018/03/03 11:07

サーバー側にデータと画像があるので、 まずテキストファイルと画像を同時にクライアントに送信する。 次にクライント側で受信して、ファイルと画像に分ける。 といういみです。
ngsvx

2018/03/03 11:24

1つのコネクションでテキストファイル、画像ファイルを送信するということですよね? 具体的なやり方は色々とありますが、要は受信側でテキストファイルと画像ファイルの区切りがわかればいいということです。 大きく分けて2種類になると思います。 1つは、バイナリデータをテキストに直して、複数のテキストデータを一定ルールで区切る方法。 代表的なものではxmlがあります。 この場合、画像ファイルはバイナリデータですので、何らかの形でテキスト形式にする必要があります。 最も簡単なのは16進数表記にしてしまうことです。ただ16進数表記にすると、データサイズが倍になります。 (1バイトのデータを2バイトで表現するため) そのため、インターネット上ではバイナリデータのテキスト化の方法として、base64という方法が使われることが多々あります。 もうひとつの方法としてはチャンク形式で、チャンクヘッダーにデータサイズを記載して、それデータを続けるという方法もあります。 この方法では、バイナリデータもバイナリのまま使うことができます。 どの方法であっても、受信側は送信側と同じ解釈でデータを戻す必要があります。 このデータの分離の作業が、結構コード量を使うので、1つのコネクションで1つのファイルを送信し、 複数のコネクションを使って全てのデータを送る方法をお勧めするわけです。
eisaku123

2018/03/03 12:24

1つのコネクションの方法として大きく分けて2種類あるということですか? >複数のコネクションを使って全てのデータを送る方法をお勧めするわけです。 複数のコネクションの方が良いということですか? そもそもコネクションの意味がはっきりわかっておらず、1回のプログラムの処理=1つのコネクション ような感じ? あとクライアントがブラウザーだとこのような複雑な処理はないと思うのですが、Android アプリだとこのようなことが一般的なのでしょうか?
ngsvx

2018/03/03 12:43

>1つのコネクションの方法として大きく分けて2種類あるということですか? そうですね。 >複数のコネクションの方が良いということですか? その方がプログラム的には簡単です。 >コネクションの意味がはっきりわかっておらず、 簡単に言えば、url.openConnection();をしてから、disconnect()するまでといったらいいですかね。 >あとクライアントがブラウザーだとこのような複雑な処理はないと思うのですが というより、ある意味ブラウザを自分で作っているようなものなので、手間がかかるのは当然と言えます。
ngsvx

2018/03/03 12:49

ついでに、もうひとつ言っておくと、1コネクション1ファイルにしておけば、それはhttpの基本的な機能であるため、 特別にサーブレットを作らなくても、httpサーバーの機能だけで送信できます。 送信側は、適切な場所に送信したいファイルをファイルを配置するだけです。
ngsvx

2018/03/03 12:53

忘れていましたが、質問者さんの知識レベルが不明だったため、普通に用語を使ってしまいましたが、 もし、わからない用語があれば、聞いてもらうか、別途質問するか、ググるかしてください。
退会済みユーザー

退会済みユーザー

2018/03/03 13:05

・q・) 多分、入門中レベル ブラウザがHTMLを表示するときに画像も同じリクエストでとってきてると思ってるようだから
eisaku123

2018/03/03 13:13

おっしゃる通りです。そう思ってました。まさに初心者です。 そこの内容ってググればありますか? あと、どこから学びなおした方がよいのでしょうか?
ngsvx

2018/03/03 13:27 編集

>そう思ってました。 では、この件について、簡単にですが補足しておきます。 例えば、http://xxx.xxx.com/aaa.htmlをwebブラウザで表示するには、 1.ブラウザは、xxx.xxx.comサーバーに対して、aaa.htmlファイルを要求(コネクトする) 2.xxx.xxx.comサーバーはaaa.htmlファイルを送信 3.ブラウザはaaa.htmlを受信 4.ブラウザはaaa.htmlの内容を解析<img>タグがあれば、src="bbb.jpg"の箇所を探し、 xxx.xxx.comサーバーに対し、bbb.jpgファイルを要求(2度目のコネクト) 5.xxx.xxx.comはbbb.jpgを送信 6.ブラウザはbbb.jpgを受信 7.ブラウザはaaa.htmlの内容に従って、画面を作成/表示 という手順となります。 >そこの内容ってググればありますか? 今の世の中、ググればたいていのことは出てくるかと思います。 まあ、理解できるかは別問題ですが。 >あと、どこから学びなおした方がよいのでしょうか? 「どこから」というのは非常に難しいです。 というのは、今回の件だけでも、いくつもの技術が複合してできているもので、それらを並行して学習しなければなりません。 ただ、単純に通信だけの話であれば、「http」をキーワードにして調べるといいかと思います。
ngsvx

2018/03/03 13:44

あまり、やりとりが長くなってもいけないので、とりあえず、今回の解決策の一例を示しておきます。 1.一回のコネクトで1ファイルという方針にする 2.サーバー側で、テキストファイル、画像ファイルを適切な場所に配置しておく 3.webブラウザで、テキストファイル、画像ファイルがダウンロードできるか確認する (urlの確認の意味も含む) 4.クライアントプログラムでは、2回コネクトしてテキストファイル、画像ファイルそれぞれを受信する URL url = new URL(.......); が2回必要です。またurlはそれぞれ異なるものになります。 テキストファイルのurlでコネクトしたらテキストの読み込み処理を、 画像ファイルのurlでコネクトしたら画像ファイルの読み込み処理を行って下さい。 なお、ストリームは使用後にcloseするのを忘れずに。
eisaku123

2018/03/03 14:08

いろいろご指導ありがとうございます。一歩一歩前進して頑張ります。
eisaku123

2018/03/04 03:17 編集

お世話になります。以下の様にしたら、できました。 ngsvxさん、asahinaさんご指導ありがとうございます。手法や知識が増えました。 @Override protected Result doInBackground(Void... voids) { Result result = new Result(); byte[] data; result.bitmap = null; result.text=null; InputStream inputStream = null; StringBuilder builder = new StringBuilder(); try { /*画像データ呼び出し*/ URL url1 = new URL("http://192.168.3.5:8080/book777/chapter3"); HttpURLConnection con2 = (HttpURLConnection)url1.openConnection(); con2.setRequestMethod("GET"); con2.connect(); inputStream = con2.getInputStream(); result.bitmap = BitmapFactory.decodeStream(inputStream); con2.disconnect();//ここで一端閉じる。 /*テキストデータ呼び出し*/ String z = edit_text.getText().toString(); String y = URLEncoder.encode(z, "UTF-8"); URL url2 = new URL("http://192.168.3.5:8080/book123/chapter14/search?keyword=" + y); HttpURLConnection con = (HttpURLConnection)url2.openConnection(); con.setRequestMethod("GET"); con.connect(); result.text ="まぐろだよ"; BufferedReader reader = new BufferedReader(new InputStreamReader(con.getInputStream(), "UTF-8")); String line; while ((line = reader.readLine()) != null){ builder.append(line); builder.append("\n"); } con.disconnect(); //ここで閉じる result.text = builder.toString(); }catch (IOException exception){ } return result; } @Override protected void onPostExecute(Result result) { imageview.setImageBitmap(result.bitmap); textView.setText(result.text); }
退会済みユーザー

退会済みユーザー

2018/03/04 03:12

朝暇じゃない・・・
eisaku123

2018/03/04 03:17

すみません、訂正しました。
ngsvx

2018/03/04 04:58

いいのではないかと思います。 ただ、ひとつだけ。 使い終わったストリームは必ず使い終わった時点でcloseしてください。 「inputStream」と「reader」です。 今回は問題にはならないでしょうが、違いシチュエーションでは問題が生じる可能性もあります。 ストリームのcloseは習慣付けるようにしてください。 以上です。 お疲れ様でした(^^)
eisaku123

2018/03/08 13:53

いろいろアドバイス、ありがとうございます。
退会済みユーザー

退会済みユーザー

2018/03/08 13:56

・q・) 最近は AutoClose ( try catch resource 文)にたよるようにしてるな
ngsvx

2018/03/09 01:11

確かにAutoCloseは便利ですが、初心者のうちは最近の技術は使わずにコーディングした方がいいような気もします。 意見の分かれるところでしょうから、絶対とは言い切れませんが。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

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

ただいまの回答率
85.50%

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

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

質問する

関連した質問