我正在使用一個 api,我想在其中顯示我的 HTML 中生成的資料。為此,我正在使用 JavaScript 創建 div 元素。顯示資訊時它沒有問題,但每次我更新頁面時,資料都會以不同的順序顯示它們。也就是說,如果我有 3 個 div,那么第一個 div 現在將出現在最后,因此每次更新頁面時順序都會發生變化。
這是我的 Javascript 代碼:
const cargar_noticias_recientes = async () => {
const noticias_recientes = document.querySelector('#pnl-body-content-card-reci');
const res = await fetch(`WebService_Default.asmx/cargar_card_noticia_recientes`, {
method: 'POST',
headers: {
'Content-Type': 'application/json'
},
body: ''
});
const datos = await res.json();
let nuevos = [...datos.d];
nuevos.map(async nuevo => {
const div = document.createElement('div');
const peticion = await fetch(`http://localhost:51482/api/values/${nuevo[3]}`, {
method: 'GET'
});
const imagen = await peticion.blob();
const url = URL.createObjectURL(imagen);
div.innerHTML = `
<div class="body-card body-card-reci ${nuevo[0]}">
<div class="card-title">
<span>Nuevo</span>
</div>
<div class="img-card">
<div class="img" style="background-image: url(${url});"></div>
</div>
<div class="content-card">
<p>
<i class="fas fa-tags"></i> ${nuevo[1]}
</p>
</div>
</div>
`
noticias_recientes.appendChild(div);
});
}
uj5u.com熱心網友回復:
可能會出現不同的順序,因為await多個map回呼中的某些-ed 承諾可能比其他承諾更快解決,從而給出不同的執行順序。
您可以使用Promise.all-- 仍然允許非 JS 異步任務彼此獨立運行,按原始順序取回結果:
const promises = nuevos.map(async nuevo => {
const div = document.createElement('div');
const peticion = await fetch(`http://localhost:51482/api/values/${nuevo[3]}`, {
method: 'GET'
});
const imagen = await peticion.blob();
const url = URL.createObjectURL(imagen);
div.innerHTML = `
<div class="body-card body-card-reci ${nuevo[0]}">
<div class="card-title">
<span>Nuevo</span>
</div>
<div class="img-card">
<div class="img" style="background-image: url(${url});"></div>
</div>
<div class="content-card">
<p>
<i class="fas fa-tags"></i> ${nuevo[1]}
</p>
</div>
</div>
`;
// Don't append to the DOM yet, but *return*
return div;
});
// Collect the DIVs in the order of the originally fetched data:
const divs = await Promise.all(promises);
// ...And populate the DOM
for (const div of divs) noticias_recientes.appendChild(div);
uj5u.com熱心網友回復:
您的問題與異步的使用有關。
nuevos.map(async nuevo => {
const div = document.createElement('div');
const peticion = await fetch(`http://localhost:51482/api/values/${nuevo[3]}`, {
method: 'GET'
});
const imagen = await peticion.blob();
const url = URL.createObjectURL(imagen);
div.innerHTML = `
<div hljs-subst">${nuevo[0]}">
<div >
<span>Nuevo</span>
</div>
<div >
<div style="background-image: url(${url});"></div>
</div>
<div >
<p>
<i ></i> ${nuevo[1]}
</p>
</div>
</div>
`
noticias_recientes.appendChild(div);
});
在此函式中,您執行提取操作。這是一個具有或多或少隨機執行時間的 HTTP 請求。完成的第一個 fetch 將是創建的第一個 div,完成的第二個 fetch 將是創建的第二個 div,依此類推。
如果您想不斷保持 div 創建的順序,則必須將其從map回呼中取出,因為每次 fetch 都不會等待前一次完成。像這樣 :
for (nuevo of nuevos) {
const div = document.createElement('div');
const peticion = await fetch(`http://localhost:51482/api/values/${nuevo[3]}`, {
method: 'GET'
});
const imagen = await peticion.blob();
const url = URL.createObjectURL(imagen);
div.innerHTML = `
<div class="body-card body-card-reci ${nuevo[0]}">
<div class="card-title">
<span>Nuevo</span>
</div>
<div class="img-card">
<div class="img" style="background-image: url(${url});"></div>
</div>
<div class="content-card">
<p>
<i class="fas fa-tags"></i> ${nuevo[1]}
</p>
</div>
</div>
`
noticias_recientes.appendChild(div);
}
這樣,每次 fetch 都會耐心等待前一次完成,并且您的 div 將始終以相同的順序創建。
請注意,它顯然沒有為此進行優化。因為您的請求不再是并行完成的,而是一個接一個。所以這個函式的執行時間將是 (avgTimeOfFetch) * nbRequestToDo 秒
如果你想要更優化的東西,你應該像在初始版本中那樣并行運行你的請求,然后按照你想要的方式對資料進行排序,然后你可以創建你的 div 并將它們插入到 DOM 中。
轉載請註明出處,本文鏈接:https://www.uj5u.com/yidong/377889.html
標籤:javascript html
