C# 在多个UnityWebRequests上迭代

C# 在多个UnityWebRequests上迭代,c#,api,unity3d,webrequest,unitywebrequest,C#,Api,Unity3d,Webrequest,Unitywebrequest,我一直在尝试让一些API通信工作。我使用UnityWebRequests是因为我想构建为WebGL,我尝试了System.Net.WebRequest,它在游戏模式下工作,但与WebGL不兼容。这可能只是一个协同程序的问题,但我将以半伪的方式向您展示我到目前为止所拥有的以及我的问题是什么: using UnityEngine; using UnityEngine.Networking; using System.Collections; using System.Collections.Gene

我一直在尝试让一些API通信工作。我使用UnityWebRequests是因为我想构建为WebGL,我尝试了System.Net.WebRequest,它在游戏模式下工作,但与WebGL不兼容。这可能只是一个协同程序的问题,但我将以半伪的方式向您展示我到目前为止所拥有的以及我的问题是什么:

using UnityEngine;
using UnityEngine.Networking;
using System.Collections;
using System.Collections.Generic;

public class scking : MonoBehaviour
{

    string tempText;
    string getUri = "https://api.opensensors.com/getProjectMessages";
    string jwtToken = "someToken";

    private void Start()
    {
        pullAllData();
    }

    IEnumerator GetDataRequest(string currentDateString, string nextDateString, string sensorID)
    {
        string requestParam = "myparameters: " + nextDateString + sensorID; // simplified dummy parameters

        using (UnityWebRequest webRequest = UnityWebRequest.Get(requestParam))
        {
            webRequest.SetRequestHeader("Authorization", "Bearer " + jwtToken);
            webRequest.SetRequestHeader("Content-Type", "application/json");

            yield return webRequest.SendWebRequest();

            // from unity api example
            string[] pages = getUri.Split('/');
            int page = pages.Length - 1;

            if (webRequest.isNetworkError)
            {
                Debug.Log(pages[page] + ": Error: " + webRequest.error);
            }
            else
            {
                Debug.Log(pages[page] + ":\nReceived: " + webRequest.downloadHandler.text);
            }

            // getting the data i pulled out of the coroutine for further manipulation
            this.tempText = webRequest.downloadHandler.text;

            // show whats been pulled
            print(this.tempText);
        }
    }

    void pullAllData()
    {
        int allDaysCount = 10;
        List<int> sensorIds; // initialized with some ids

        for(int i = 0; i < allDaysCount - 1; i++)
        {
            for(int j = 0; j < sensorIds.Count; j++)
            {
                StartCoroutine(GetDataRequest(i, i + 1, sensorIds[j]));

                // show whats been pulled
                print(this.tempText);

                // parse json string this.tempText etc.
            }
        }

    }
}
输出按时间排序

从pullAddData中打印:空

然后是协同程序中的下一个print:jsonim

基本上,协同程序花费的时间太长,而且对于我的循环来说太晚,无法继续,因为我得到了一个空值,我当然无法解析或管理我的数据。或者也许我的整个工作都有缺陷,在这种情况下,如何恰当地做到这一点


非常感谢你在这方面的帮助。好样的,菲利普,如果你想等他们来,请平行核对我的答案

如果您还想一个接一个地等待它们,您可以简单地将它们打包成一个更大的协同程序:

void pullAllData()
{
    int allDaysCount = 10;
    List<int> sensorIds; // initialized with some ids

    // start the "parent" Coroutine
    StartCoroutine(GetAllData(allDaysCount, sensorIds));
}

IEnumerator GetAllData(int allDaysCount, List<int> sensorIds)
{
    for(int i = 0; i < allDaysCount - 1; i++)
    {
        for(int j = 0; j < sensorIds.Count; j++)
        {
            // Simply run and wait for this IEnumerator
            // in order to execute them one at a time
            yield return GetDataRequest(i, i + 1, sensorIds[j]);

            // show whats been pulled
            print(this.tempText);

            // parse json string this.tempText etc.
        }
    }

    // Maybe do something when all requests are finished and handled
}

IEnumerator GetDataRequest(string currentDateString, string nextDateString, string sensorID)
{
    string requestParam = "myparameters: " + nextDateString + sensorID; // simplified dummy parameters

    using (UnityWebRequest webRequest = UnityWebRequest.Get(requestParam))
    {
        webRequest.SetRequestHeader("Authorization", "Bearer " + jwtToken);
        webRequest.SetRequestHeader("Content-Type", "application/json");

        yield return webRequest.SendWebRequest();

        // from unity api example
        string[] pages = getUri.Split('/');
        int page = pages.Length - 1;

        if (webRequest.isNetworkError)
        {
            Debug.Log(pages[page] + ": Error: " + webRequest.error);
        }
        else
        {
            Debug.Log(pages[page] + ":\nReceived: " + webRequest.downloadHandler.text);
        }

        // getting the data i pulled out of the coroutine for further manipulation
        this.tempText = webRequest.downloadHandler.text;

        // show whats been pulled
        print(this.tempText);
    }
}

您需要在获得结果后打印它,而不是假设它的InstamaticStartCorroutine只会启动伪线程并立即返回。因此,如果您仅在启动请求后尝试在下一行打印请求的结果,它将永远不会收到结果。数据的解析和操作必须在GetDataRequest中的yield语句之后进行。在这里,您可以确保服务器响应已收到。您的意思是:并行?谢谢@BenjaminZach好主意。它实际上像你说的那样工作得很好。我仍然觉得必须有一个更迷人的解决办法。@derHugo这太棒了!我想在我的脑海中,我希望一步一步地完成每个请求,等待数据进入,处理它,将它存储在某个列表中,然后继续执行下一个UnityWebRequest。