JavaScript宝可梦图鉴排序问题排查及其他排序方式咨询
修复宝可梦图鉴排序问题 + 额外排序思路
现有代码的核心问题
- 未保留宝可梦原始数据集合:当前代码直接将数据渲染为DOM元素,没有存储原始数据数组,导致排序时
pokemon.sort完全无效(pokemon是单个DOM元素,不是数据集合) - 排序后未正确重新渲染:事件监听里的
createPokemonCard(data)无意义,data未定义,也未清空原有卡片再重新生成 - 冗余变量定义:
sortInput被重复声明,属于无效代码
修复后的完整代码
修复后的JavaScript代码
const pokeContainer = document.getElementById('poke_Container') const poke_Num = 150 const sortInput = document.getElementById("filter-Buttons") // 新增:存储所有宝可梦原始数据的数组,作为排序操作的基础 const allPokemon = [] const cardDetails = async () => { for (let i = 1; i <= poke_Num; i++) { await getPokemon(i) } // 初始渲染所有卡片 renderPokemonCards(allPokemon) } const getPokemon = async (id) => { const url = `https://pokeapi.co/api/v2/pokemon/${id}`; const response = await fetch(url); const data = await response.json(); // 将数据存入数组,而非直接渲染 allPokemon.push(data) } cardDetails(); // 拆分渲染函数:负责清空容器 + 根据传入的数组批量生成卡片 function renderPokemonCards(pokemonList) { pokeContainer.innerHTML = '' pokemonList.forEach(data => createPokemonCard(data)) } function createPokemonCard(data) { const pokemon = document.createElement('div') pokemon.classList.add('pokemon') const name = data.name[0].toUpperCase() + data.name.slice(1); const poketure = data.sprites["front_default"]; const poketype = data.types.map((type) => type.type.name).join(" ") const pokemonInnerHTML = ` <div class='image-Container'> <img src="${poketure}" alt="${name}"> </div> <div class='info'> <h3 class='poke-Name'>${name}</h3> <span class="poke-id">#${data.id.toString().padStart(3, "0")}</span> <br> <div class="poke-type">Type: ${poketype}</div> </div> ` pokemon.innerHTML = pokemonInnerHTML; pokeContainer.appendChild(pokemon); } sortInput.addEventListener('change', (event) =>{ const sortBy = event.target.value // 复制原始数组,避免修改原始数据集合(可选,保留初始顺序备份) let sortedPokemon = [...allPokemon] switch (sortBy) { case 'id-asc': sortedPokemon.sort((a, b) => a.id - b.id) break case 'id-desc': sortedPokemon.sort((a, b) => b.id - a.id) break case 'name-asc': // 用localeCompare替代手动字符串比较,代码更简洁且支持多语言排序 sortedPokemon.sort((a, b) => a.name.localeCompare(b.name)) break case 'name-desc': sortedPokemon.sort((a, b) => b.name.localeCompare(a.name)) break } // 调用渲染函数展示排序结果 renderPokemonCards(sortedPokemon) })
关键改动说明
- 新增
allPokemon数组存储原始数据,这是排序功能的核心基础 - 拆分
renderPokemonCards函数,统一处理容器清空和卡片批量生成,避免重复代码 - 排序时复制原始数组,防止修改初始数据集合
- 用
localeCompare简化字符串排序逻辑,兼容性更好 - 移除冗余的
sortInput声明
额外排序方式建议
除了ID和名称排序,还可以实现这些实用的排序逻辑:
- 按主类型排序:先按宝可梦的第一个类型分组,同类型内再按ID/名称排序
// 示例:主类型升序,同类型按ID升序 sortedPokemon.sort((a, b) => { const typeA = a.types[0].type.name const typeB = b.types[0].type.name if (typeA !== typeB) { return typeA.localeCompare(typeB) } return a.id - b.id }) - 按身高/体重排序:利用API返回的
height和weight字段排序// 身高升序 sortedPokemon.sort((a, b) => a.height - b.height) // 体重降序 sortedPokemon.sort((a, b) => b.weight - a.weight) - 按名称长度排序:比较名称的字符长度
sortedPokemon.sort((a, b) => a.name.length - b.name.length)
内容的提问来源于stack exchange,提问作者Mekayla
相关产品推荐
相关产品推荐

