1

C# で非同期メソッドがどのように機能するかについて質問があります。convertAddressToCoordinate メソッドを取得して myLocation 変数を GeoCoordinate に設定しようとしています。ただし、 myLocation 値が設定される前であっても、compareDistance メソッドが呼び出されます。compareDistance() を呼び出す前に、myLocation の値が null でないことを確認するにはどうすればよいですか?

public GeoCoordinate myLocation = null;

public void returnClosestCurrent(string address)
 {

     convertAddressToCoordinate(address);
     compareDistance(myLocation);

 }

 public void convertAddressToCoordinate(string add)
 {
    WebClient wc = new WebClient();
     wc.DownloadStringCompleted += wc_DownloadStringCompleted;
     wc.DownloadStringAsync(new Uri("http://maps.googleapis.com/maps/api/geocode/json?address=1600+bay+st&sensor=false"));


 }

 void wc_DownloadStringCompleted(object sender, DownloadStringCompletedEventArgs e)
 {

    XDocument xdoc = XDocument.Parse(e.Result, LoadOptions.None);

     var data = from query in xdoc.Descendants("location")
                 select new Location
                 {
                     lat = (string)query.Element("lat"),
                     lng = (string)query.Element("lng")
                 };

     GeoCoordinate destinationGeo = new GeoCoordinate(Convert.ToDouble(data.ElementAt(0).lat), Convert.ToDouble(data.ElementAt(0).lng));

     myLocation = destinationGeo;


 }
4

3 に答える 3

2

await キーワードを使用して、非同期タスクの値を取得できます

http://msdn.microsoft.com/en-us/library/vstudio/hh156528.aspx

于 2013-03-28T01:22:07.307 に答える
1

あなたのコードを見ると、メソッドcompareDistance(myLocation);の最後でのみ呼び出す必要があるようです。wc_DownloadStringCompleted

その変更後、すべてが正常に機能するはずです。

于 2013-03-28T01:35:16.427 に答える
1

awaitあなたはしたいでしょうwc.DownloadStringAsync

public async Task returnClosestCurrent(string address)
{
    await convertAddressToCoordinate(address)
              .ContinueWith(t => compareDistance(myLocation));
}

public async Task convertAddressToCoordinate(string add)
{
    WebClient wc = new WebClient();
    wc.DownloadStringCompleted += wc_DownloadStringCompleted;
    await wc.DownloadStringAsync(new Uri("http://maps.googleapis.com/maps/api/geocode/json?address=1600+bay+st&sensor=false"));
}

async/のパターンは、コードがすべてを/awaitに変える傾向がありますasyncawait

使用するためにリファクタリングできますWebClient.DownloadStringTaskAsync

public async Task ReturnClosestCurrent(string address)
{
    await convertAddressToCoordinate(address)
            .ContinueWith(t => compareDistance(t.Result));
}

public async Task<GeoCoordinate> ConvertAddressToCoordinate(string add)
{
    WebClient wc = new WebClient();
    wc.DownloadStringCompleted += wc_DownloadStringCompleted;
    var content = await wc.DownloadStringTaskAsync(new Uri("http://maps.googleapis.com/maps/api/geocode/json?address=1600+bay+st&sensor=false"));

    return ParseContent(content);
}

private GeoCoordinate ParseContent(string content)
{
    XDocument xdoc = XDocument.Parse(content, LoadOptions.None);

    var data = from query in xdoc.Descendants("location")
             select new Location
             {
                 lat = (string)query.Element("lat"),
                 lng = (string)query.Element("lng")
             };

    GeoCoordinate destinationGeo = new GeoCoordinate(Convert.ToDouble(data.ElementAt(0).lat), Convert.ToDouble(data.ElementAt(0).lng));

    return destinationGeo;
}
于 2013-03-28T02:03:06.107 に答える