取消隐藏和加载webview的顺序是否会影响性能?(Does the order of unhiding and loading a webview affect performance?)
在我的应用程序中,我有一个带有进度条的加载视图,因此用户可以观看PDF的下载进度。 下载完成后,我取消隐藏webview,然后调用loadRequest。 我只是想知道是否有任何区别:
[self.webView setHidden:NO];
[self.webView loadRequest:[NSURLRequest requestWithURL:localURL]];
与
[self.webView loadRequest:[NSURLRequest requestWithURL:localURL]];
[self.webView setHidden:NO];
我问,因为我假设loadRequest发生在自己的队列中,所以我认为没有任何明显的差异。
In my app I have a loading view with a progress bar so the user can watch a PDF's download progress. When the download completes I unhide the webview and then call loadRequest. I was just wondering if there is any difference between:
[self.webView setHidden:NO];
[self.webView loadRequest:[NSURLRequest requestWithURL:localURL]];
Versus
[self.webView loadRequest:[NSURLRequest requestWithURL:localURL]];
[self.webView setHidden:NO];
I ask because I assumed loadRequest happens in its own queue, so I thought there couldn't be any visible differences.
原文:https://stackoverflow.com/questions/17335166
最满意答案
当我将其注销时,为什么我的问题变量为空? 有明显的结果与它相结合。
这里的一个主要问题是
.concat()
返回一个新数组。 它不会将项添加到现有阵列上。你可以改变这个:
issues.concat(JSON.parse(body).issues);
对此:
issues = issues.concat(JSON.parse(body).issues);
确保保留新的连锁数组。 这是一个非常常见的错误。
您也可能在数组中遇到排序问题,因为您正在运行
for
循环,它会同时启动一大堆请求,结果可能会或可能不会以正确的顺序返回。 您仍将获得正确的问题总数,但它们可能不符合要求的顺序。 我不知道你是否有问题。 如果这是一个问题,我们也可以建议修复。一个更普遍的问题:这种方法是解决我想要实现的目标的最佳方式吗? 我认为即使我的代码确实有效,异步性的本质意味着结果可能以错误的顺序连接起来。
除了也可以修复的订购问题,这是一种合理的做事方式。 我们需要了解有关您的API的更多信息,以了解这是否是使用API获取结果的最有效方式。 通常,您希望避免对同一服务器进行N次重复API调用,而是进行一次API调用以获取所有结果。
我应该只使用同步请求库吗?
绝对不。 node.js需要学习如何进行异步编程。 对于大多数人来说,这是一个学习步骤,但是你是如何从node.js获得最佳性能的,应该学习和使用它。
这是一种使用promises进行同步和错误传播的可靠顺序收集所有结果的方法(这对于node.js中的异步处理非常有用):
// promisify the request() function so it returns a promise // whose fulfilled value is the request result function requestP(url) { return new Promise(function(resolve, reject) { request(url, function(err, response, body) { if (err || response.statusCode !== 200) { reject({err: err, response: response}); } else { resolve({response: response, body: body}); } }); }); } Donedone.prototype.getAllActiveIssues = function() { var url = this.url; return requestP(url + `/issues/all_active.json?take=500`).then(function(results) { var data = JSON.parse(results.body); var totalIssues = data.total_issues; var promises = []; for (let i = 0; i < totalIssues; i+= 500) { promises.push(requestP(url + `/issues/all_active.json?skip=${i}&take=500`).then(function(results) { return JSON.parse(results.body).issues; })); } return Promise.all(promises).then(function(results) { // results is an array of each chunk (which is itself an array) so we have an array of arrays // now concat all results in order return Array.prototype.concat.apply([], results); }) }); } xxx.getAllActiveIssues().then(function(issues) { // process issues here }, function(err) { // process error here })
Why is my issues variable empty when I log it out? There are clearly results to concatenate with it.
A main problem here is that
.concat()
returns a new array. It doesn't add items onto the existing array.You can change this:
issues.concat(JSON.parse(body).issues);
to this:
issues = issues.concat(JSON.parse(body).issues);
to make sure you are retaining the new concatenated array. This is a very common mistake.
You also potentially have sequencing issues in your array because you are running a
for
loop which is starting a whole bunch of requests at the same time and results may or may not arrive back in the proper order. You will still get the proper total number of issues, but they may not be in the order requested. I don't know if that is a problem for you or not. If that is a problem, we can also suggest a fix for that.A more general question: is this approach the best way to go about what I'm trying to achieve? I figured that even if my code did work, the nature of asynchronicity means it's entirely possible for the results to be concatenated in the wrong order.
Except for the ordering issue which can also be fixed, this is a reasonable way to do things. We would have to know more about your API to know if this is the most efficient way to use the API to get your results. Usually, you want to avoid making N repeated API calls to the same server and you'd rather make one API call to get all the results.
Should I just use a synchronous request library?
Absolutely not. node.js requires learning how to do asynchronous programming. It is a learning step for most people, but is how you get the best performance from node.js and should be learned and used.
Here's a way to collect all the results in reliable order using promises for synchronization and error propagation (which is hugely useful for async processing in node.js):
// promisify the request() function so it returns a promise // whose fulfilled value is the request result function requestP(url) { return new Promise(function(resolve, reject) { request(url, function(err, response, body) { if (err || response.statusCode !== 200) { reject({err: err, response: response}); } else { resolve({response: response, body: body}); } }); }); } Donedone.prototype.getAllActiveIssues = function() { var url = this.url; return requestP(url + `/issues/all_active.json?take=500`).then(function(results) { var data = JSON.parse(results.body); var totalIssues = data.total_issues; var promises = []; for (let i = 0; i < totalIssues; i+= 500) { promises.push(requestP(url + `/issues/all_active.json?skip=${i}&take=500`).then(function(results) { return JSON.parse(results.body).issues; })); } return Promise.all(promises).then(function(results) { // results is an array of each chunk (which is itself an array) so we have an array of arrays // now concat all results in order return Array.prototype.concat.apply([], results); }) }); } xxx.getAllActiveIssues().then(function(issues) { // process issues here }, function(err) { // process error here })
相关问答
更多-
WebDriver测试是端到端,黑盒子,用户界面测试。 如果您的页面依赖于外部网关,您将拥有一个服务和模型来包装该网关,以便在整个系统中使用,并且您可能已经在测试中引用了模型。 鉴于网关是时间相关的,您应该在测试中使用api层所消耗的服务,并且只需检查网关随时返回的信息是否显示在as页面上,就像您期望的那样。 您将进行单元测试以正确检查响应模型。 如您所愿,强制性的“这可能是不可能的”:鉴于您的网关所受到的变化程度,您可能需要降低准确性或在测试中引入某种形式的刷新,因为这两个呼叫将到达稍微分开。 考虑到不可 ...
-
如何按请求的顺序将异步响应推送到数组中?(How do you push asynchronous responses into an array in the order they were requested?)[2021-12-25]
.forEach方法包含一个索引,因此您可以使用它来填充TheCurrentPrice : Contracts.forEach(function (Contract, index) { Contract.Price(function (error, result) { TheCurrentPrice[index] = result; }); }); 但请注意,您仍然需要某种形式的同步来告诉您何时已获得所有价格。 因此,更好的解决方案可能是将Price的调用Price为 ... -
区分没有数字的小村庄和街道之间的API响应(Differentiate API responses between hamlets and street without number)[2022-03-10]
简短的回答 - 您的哈姆雷特示例实际上正在解决一条街道: 地图链接 回答你的一般问题(猜测你在其他地方发生了这种情况,而不是街道),这是如何判断地理编码API如何确定部分匹配。 如果你得到一条路线,它应该意味着你已经返回了一条街道(有或没有号码)。 哈姆雷特应该显示为一个sublocality或neighborhood如果不是它自己的地方(在加拿大这是我所见过的): 邻里 sublocality *请注意,这些在加拿大不是有效的邮寄地址,这使我的示例与您指定的标准略有不同。 要知道路由是完全匹配还是猜测是状 ... -
无论您创建URL对象的顺序如何,对同一服务器的所有请求都将被流水线化,您无法控制下载顺序。此外,某些URL可能会被缓存,而其他URL可能需要转到远程服务器。 您需要做的是维护一个包含实际数据映射URL的可变数组或字典,然后等待所有URL完全下载,然后按已知顺序迭代。 You cannot control the download order in the sense that all the requests to the same server will be pipelined no matter wh ...
-
摆脱setRequestHeader var req = new XMLHttpRequest(); var payload = {location: null, temperature:null, humidity:null}; req.open("GET", "http://api.openweathermap.org/data/2.5/weather?q=02143,us&appid=fa7d80c48643dfadde2cced1b1be6ca1", true); //req ...
-
当我将其注销时,为什么我的问题变量为空? 有明显的结果与它相结合。 这里的一个主要问题是.concat()返回一个新数组。 它不会将项添加到现有阵列上。 你可以改变这个: issues.concat(JSON.parse(body).issues); 对此: issues = issues.concat(JSON.parse(body).issues); 确保保留新的连锁数组。 这是一个非常常见的错误。 您也可能在数组中遇到排序问题,因为您正在运行for循环,它会同时启动一大堆请求,结果可能会或可能不会 ...
-
在仔细阅读了异步示例之后,我现在看到它重复读取,直到遇到成功读取0字节为止。 所以要回答我自己的问题,你必须一遍又一遍地调用InternetReadFile(),并为同步或异步响应做好准备。 After a more careful reading of the asynchronous example, I see now that it is reading repeatedly until a successful read of 0 bytes is encountered. So to answe ...
-
区分公共API响应与经过身份验证的API响应(Differentiating public API responses from authenticated API responses)[2023-02-18]
第一种行为使用状态代码200,第二种行为使用206是否可以接受? 不,这是不可接受的。 206 Partial Content是响应对来自完整响应的某些特定字节范围的显式请求而给出的状态。 如第10.2.7节所述 : 该请求必须包含一个Range标题字段( 第14.35节 ),表示所需的范围 在您的情况下,“未经身份验证的请求” 本身不会包含Range标头,因此206响应将违反规范。 Is it acceptable to use a status code of 200 for the first beh ... -
URLDownloadToFile API,如何异步使用?(URLDownloadToFile API, how can it be used asynchronously?)[2022-02-20]
请改用URLOpenPullStream 。 Use URLOpenPullStream instead. -
在处理异步协议时,通常需要设计协议,以便每个请求都有一个唯一的ID,该ID包含在请求数据中并在响应中发回。 这样,您可以不按顺序接收响应,甚至收到未经请求的消息。 发送请求时,将请求ID放在某个列表中,以及响应到达时将调用的回调。 当您获得数据事件时,将原始数据附加到缓冲区,然后仅从缓冲区中解析出完整的消息,留下不完整的消息以便以后完成。 对于解析出的每个完整消息,检查它是否具有请求ID。 如果不是,则消息是未经请求的,因此请相应地处理。 否则,在列表中查找请求ID,如果找到,则调用与之关联的回调。 Whe ...