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

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

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

C#はマルチパラダイムプログラミング言語の1つで、命令形・宣言型・関数型・ジェネリック型・コンポーネント指向・オブジェクティブ指向のプログラミング開発すべてに対応しています。

Q&A

解決済

1回答

4806閲覧

リフレクションで非同期のプライベートメソッドを呼び出したい

kazuya_

総合スコア78

C#

C#はマルチパラダイムプログラミング言語の1つで、命令形・宣言型・関数型・ジェネリック型・コンポーネント指向・オブジェクティブ指向のプログラミング開発すべてに対応しています。

0グッド

0クリップ

投稿2017/06/16 09:02

public型は下記のasynctest1()コードでいけましたが、private型でprivateasynctest1() のように書きましたが動きませんどう書けばいいのでしょうか?

using System; using System.Collections.Generic; using System.ComponentModel; using System.Data; using System.Drawing; using System.Linq; using System.Text; using System.Threading.Tasks; using System.Windows.Forms; namespace AsyncPrivate { class Program { static void Main(string[] args) { } } public class PrivateAccess {   public async Task<int> ComplexAsyncTask() { Func<int> asyncJob = () => { return 123; }; Func<int> asyncJob2 = () => { return 123; }; int ret1 = await Task.Run(asyncJob); int ret2 = await Task.Run(asyncJob2); return ret1 + ret2; }         /// うまくいかない paivate async Task<int> PrivateComplexAsyncTask() { Func<int> asyncJob = () => { return 123; }; Func<int> asyncJob2 = () => { return 123; }; int ret1 = await Task.Run(asyncJob); int ret2 = await Task.Run(asyncJob2); return ret1 + ret2; } } } using System; using System.Threading.Tasks; using AsyncPrivate; using Microsoft.Pex.Framework; using Microsoft.Pex.Framework.Validation; using Microsoft.VisualStudio.TestTools.UnitTesting; namespace AsyncPrivate.Tests { [TestClass()] public class PrivateAccessTests { [TestMethod()] public async Task asynctest1() { PrivateAccess pr = new PrivateAccess(); int s = await pr.ComplexAsyncTask(); s = s; }         /// うまくいかない [TestMethod()] public void privateasynctest1() { PrivateObject po = new PrivateObject(new PrivateAccess()); Task<int> actual = po.Invoke("PrivateComplexAsyncTask") as Task<int>; actual = actual; } } }

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

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

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

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

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

guest

回答1

0

ベストアンサー

csharp

1 2 [TestMethod()] 3 public void privateasynctest1() 4 { 5 PrivateObject po = new PrivateObject(new PrivateAccess()); 6 Task<int> actual = po.Invoke("PrivateComplexAsyncTask") as Task<int>; 7 int actualValue = actual.Result; 8 9 Assert.AreEqual(246, actualValue); 10 11 } 12 13

TaskのResultを取得していないのが問題なのではないでしょうか?


追記
asyncなテストを構築したいのなら、

csharp

1 [TestMethod] 2 public async Task PrivateAsyncTest() 3 { 4 PrivateObject po=new PrivateObject(new PrivateAccess()); 5 6 var actual = await (po.Invoke("PrivateComplexAsyncTask") as Task<int>); 7 8 Assert.AreEqual(246, actual); 9 10 } 11 12

概ねこのような形になるかと。
void戻しにすると、Test runnerが非同期状態のテストを待機不可能になるため、戻り値をTaskにする必要があります。

投稿2017/06/16 10:36

編集2017/06/16 13:52
Tokeiya3

総合スコア260

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

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

kazuya_

2017/06/16 11:45

ありがとうございました。 デバッガでresultは見た時NULLになっていたので失敗してるものと思っていました。 この場合は、ASYNCがいらないのはなぜですかね? 結局、ASYNCが入った形にコンパイルされてるんでしょうか。
Tokeiya3

2017/06/16 13:33 編集

async/awaitは非同期のステートマシンを構築するための構文なので、コンパイルされた結果にasyncそのものが入ってるわけではないです。その点お間違えなきよう。 デバッガで止まっている場合、非同期で実行中のTaskもデバッガの設定に依存しますが一般的に停止しています。従って、Resultはデバッガアタッチでブレークした状態では取れないのでしょう(逆に言えば、タイミングによってはResultが有効なケースもあるでしょう)。 以下蛇足ですが、本来PrivateなメソッドはPrivate足る理由があるので隠蔽されているのだと思慮します。 テストだから逢えて呼ぶというのは理解できますが、あくまでイレギュラーなコトをしていることは承知しておく必要があると思います。
kazuya_

2017/06/16 23:39

ありがとうございました。asyncJob2に遅延 System.Threading.Thread.Sleep(3000);を 入れて、デバッグしてみました。3秒後に下記ブレークポイントで止まりました。 Task<int> actual = po.Invoke("PrivateComplexAsyncTask") as Task<int>; ● int actualValue = actual.Result; //ここでBREAKPOINTいれるととactualは未計算 ● Assert.AreEqual(246, actualValue);//ここだと計算されている 遅延実行されてるようです。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

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

ただいまの回答率
85.50%

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

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

質問する

関連した質問