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

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

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

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

Android

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

Q&A

解決済

2回答

4695閲覧

android 非同期処理の処理の流れについて

rashild

総合スコア24

Java

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

Android

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

0グッド

1クリップ

投稿2019/06/18 12:01

編集2019/06/18 14:13

前提・実現したいこと

NFCタグを読み取るandroidアプリを作っています。
MainActivity.javaからAsyncTaskを拡張したクラスで非同期処理としてhttp通信を行い、responseを格納した変数をMainActivity.javaで使えるようにしたかったのでこちらのサイトのコードを参考にさせていただきました。
https://akira-watson.com/android/httpurlconnection-post.html
わからないことはAsyncTask側のresult変数をMainActivity.javaがなぜ使うことができているのかという所です。
コードは一部だけ抜粋してます。(動いてはいるので、全体コードではないです。理解のための教えていただけると嬉しいです。)
わかりづらい場合は全コード載せたいと思います。

MainActivity.java

java

1private UploadTask task; 2private TextView textView; 3private EditText editText; 4String url = "post先のURLです"; 5 6@Override 7protected void onCreate(Bundle savedInstanceState) { 8 super.onCreate(savedInstanceState); 9 setContentView(R.layout.activity_main); 10 11 editText = findViewById(R.id.uriname); 12 13 Button post = findViewById(R.id.post); 14 15 // ボタンをタップして非同期処理を開始 16 post.setOnClickListener(new View.OnClickListener() { 17 @Override 18 public void onClick(View v) { 19 String param0 = editText.getText().toString(); 20 21 if(param0.length() != 0){ 22 task = new postTask(); 23 task.setListener(createListener()); 24 //System.out.println(task.getClass()); 25 task.execute(param0); 26 } 27 28 } 29 }); 30 } 31 32private postTask.Listener createListener() { 33 return new postTask.Listener() { 34 @Override 35 public void onSuccess(String result) { 36 textView.setText(result); 37 } 38 }; 39 }

postTask.java

java

1public class postTask extends AsyncTask<String, Void, String> { 2 3private Listener listener; 4 5//この上にdoInBackgroundメソッドがあり、そこの戻り値であるresultをonPostExecute 6//の引数として受け取ることは理解しています。 7 8// 非同期処理が終了後、結果をメインスレッドに返す 9 @Override 10 protected void onPostExecute(String result) { 11 super.onPostExecute(result); 12 13 if (listener != null) { 14 listener.onSuccess(result); 15 } 16 } 17 18 void setListener(Listener listener) { 19 this.listener = listener; 20 } 21 22 interface Listener { 23 void onSuccess(String result); 24 } 25}

私の考え

私の考えとしては、MainActivity.javaでresult変数を使うことができていますが、postTaskのオブジェクトをexecuteする前にsetListenerでListenerの中の処理を書いているので、実際にはMainActivity.javaにresult変数は渡しておらず、postTask.javaのなかで処理は完結しているんじゃないかと思いました。

なぜ、MainActivity.javaでresult変数が使えるのでしょうか?
回答よろしくお願いします。

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

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

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

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

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

keicha_hrs

2019/06/18 14:11

postTask.javaとして示されているソースに記述されているクラス名がUploadTaskになっていますが、これはpostTaskの書き間違いですか?また、この質問にKotlinは関係していないようですから、Kotlinタグは外すべきと思います。
rashild

2019/06/18 14:12

postTask.javaの間違いです。訂正します。
keicha_hrs

2019/06/18 14:37

あと、「実際にはMainActivity.javaにresult変数は渡しておらず」とお考えになっているのがよくわからないのですが、AsyncTaskのdoInBackground()が完了すると、onPostExecute()が呼ばれます。今、お示しのコードにもonPostExecute()があって、その中でlistener.onSuccess(result);という処理があるわけですが、「これがMainActivity.javaにresultを渡している部分である」ということを納得できない、ということなのでしょうか?
rashild

2019/06/18 14:48

はい、onPostExecute()はどのようにしてMainActivity.javaにresultを渡しているのか理解できていないです。
keicha_hrs

2019/06/18 14:50

Javaのinterfaceというものは十分理解されているのでしょうか?interfaceの理解度の問題のような気がしますが。
guest

回答2

0

ベストアンサー

onPostExecute()はどのようにしてMainActivity.javaにresultを渡しているのか理解できていない

ということから、Javaにおけるinterfaceを十分理解されていないのではないか?と想像しました。postTask.javaには

java

1 interface Listener { 2 void onSuccess(String result); 3 }

という記述がありますが、これはonSuccess()というメソッドの宣言だけはするが、実装は他のクラスに委ねる記述になります。その実装を実際に行っているのが、MainActivity.javaの

java

1 private postTask.Listener createListener() { 2 return new postTask.Listener() { 3 @Override 4 public void onSuccess(String result) { 5 textView.setText(result); 6 } 7 }; 8 }

の部分になります。ここで「Listenerインターフェースを実装した匿名クラスを作成し、onSuccess()をオーバーライドし、その匿名クラスのインスタンスを生成する」という作業を一挙に行っています。ちょっとこの部分がわかりにくいかもしれません。

postTask.javaのsetListener()メソッドは、このMainActivity.java側で生成されたインスタンスを変数listenerに代入しています。

そして、要となる

java

1 @Override 2 protected void onPostExecute(String result) { 3 super.onPostExecute(result); 4 5 if (listener != null) { 6 listener.onSuccess(result); 7 } 8 }

の処理では、先に代入された変数listenerを参照して、MainActivity.java側で実装されたonSuccess()を呼び出しています。その引数としてresultを渡しているわけですから、この時点で「MainActivity.javaにresult変数を渡す」ことが達成されます。

コードの書き方の問題でわかりにくければ、MainActivity.javaを

java

1// MainActivityにpostTask.Listenerをimplements(実装)する 2public class MainActivity extends AppCompatActivity implements postTask.Listener { 3 4(中略) 5 6 if(param0.length() != 0){ 7 task = new postTask(); 8 task.setListener(this); // 引数をthisにする 9 //System.out.println(task.getClass()); 10 task.execute(param0); 11 } 12 13(中略) 14 /* このメソッドはコメントアウト 15 private postTask.Listener createListener() { 16 return new postTask.Listener() { 17 @Override 18 public void onSuccess(String result) { 19 textView.setText(result); 20 } 21 }; 22 } 23 */ 24 25 // MainActivityのメソッドとして実装 26 @Override 27 public void onSuccess(String result) { 28 textView.setText(result); 29 } 30}

とすると、onSuccess()はMainActivity.javaが持つメソッドを呼んでいるのだ、ということがわかりやすくなるかもしれません。

投稿2019/06/19 13:20

keicha_hrs

総合スコア6768

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

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

rashild

2019/06/20 11:26

大変丁寧に解説していただいてありがとうございます。 コードをわかりやすく書き換えてもらったので理解できました。
guest

0

コードとしてのクラスと, 実行単位としてのスレッドを混在されてはいませんでしょうか.

スレッドとしましては, textView.setText(result); まで postTask のスレッドで「完結」しています.

コードとしましては, public void onSuccess(String result) は MainActivity.java に書かれていますので, MainActivity.javaにresult変数は渡して いると言えると思います.

投稿2019/06/19 01:53

jimbe

総合スコア12625

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

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

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

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

ただいまの回答率
85.48%

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

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

質問する

関連した質問