You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

JavaScript:多对象JSON数组选中区域的数组长度读取异常

解决下拉框联动中获取区域对应城市数组长度返回undefined的问题

问题根源

你的myObj是一个数组,数组里的每个元素都是单个键值对的对象(键是区域名称,值是城市数组)。当你用myObj[region]拿到的是这个对象,不是城市数组——对象本身没有.length属性,所以调用allCities.length会返回undefined,但直接打印allCities会显示这个包含数组的对象。

修正方案

1. 正确获取城市数组

在fillCities函数里,拿到区域对象后,提取出里面的城市数组:

var allCitiesObj = myObj[region];
var allCities = Object.values(allCitiesObj)[0]; // 提取对象里的数组

因为每个区域对象只有一个键值对,所以Object.values取第一个元素就是我们要的城市数组,此时allCities.length就能正常获取长度了。

2. 修复城市下拉框的选项内容

原来的代码直接把city对象塞到option里,会显示[object Object],应该用city.cityName作为显示文本和value:

cities.innerHTML += "<option value=\"" + city.cityName + "\">" + city.cityName + "</option>";

3. (可选)优化区域下拉框的初始化逻辑

可以把区域名称直接作为option的value,这样后续获取更直观,不用依赖索引:

Object.keys(myObj).forEach(function(key) {
  var regionName = Object.getOwnPropertyNames(myObj[key])[0];
  regions.innerHTML += "<option value=\"" + regionName + "\">" + regionName + "</option>";
});

对应的fillCities函数里,需要遍历myObj找到匹配区域名称的对象:

function fillCities(val) {
  var cities = document.getElementById("m_cities");
  cities.innerHTML = " <option value='0'>اختر مدينة التوصيل</option>";
  // 找到匹配区域名称的对象
  var regionObj = myObj.find(item => Object.keys(item)[0] === val);
  var allCities = Object.values(regionObj)[0];
  console.log(allCities.length);

  for (var i = 0; i < allCities.length; i++) {
    var city = allCities[i];
    cities.innerHTML += "<option value=\"" + city.cityName + "\">" + city.cityName + "</option>";
  }
}

修改后的完整代码

JavaScript代码

const myJSON = '[' +
  '{"المنطقة الشرقية":[' +
  '{ "cityName":"الدمام","deliveryTime":"1" },' +
  '{ "cityName":"الخبر","deliveryTime":"1" },' +
  '{ "cityName":"القطيف","deliveryTime":"1" },' +
  '{ "cityName":"صفوى","deliveryTime":"1" },' +
  '{ "cityName":"سيهات","deliveryTime":"1" },' +
  '{ "cityName":"عنك","deliveryTime":"1" },' +
  '{ "cityName":"الظهران","deliveryTime":"1" },' +
  '{ "cityName":"الجبيل","deliveryTime":"1" },' +
  '{ "cityName":"الهفوف","deliveryTime":"1" },' +
  '{ "cityName":"رأس تنورة","deliveryTime":"1" },' +
  '{ "cityName":"بقيق","deliveryTime":"1" },' +
  '{ "cityName":"المبرز","deliveryTime":"1" },' +
  '{ "cityName":"رحيمة","deliveryTime":"1" },' +
  '{ "cityName":"الأحساء","deliveryTime":"1" },' +
  '{ "cityName":"الخفجي","deliveryTime":"1" },' +
  '{ "cityName":"النعيرية","deliveryTime":"1" },' +
  '{ "cityName":"تاروت","deliveryTime":"1" }' +

  ']},' +
  '{"المنطقة الوسطى":[' +
  '{ "cityName":"الرياض","deliveryTime":"" },' +
  '{ "cityName":"الخرج","deliveryTime":"" },' +
  '{ "cityName":"بريدة","deliveryTime":"" },' +
  '{ "cityName":"عنيزة","deliveryTime":"" },' +
  '{ "cityName":"الرس","deliveryTime":"" },' +
  '{ "cityName":"المجمعة","deliveryTime":"" }' +

  ']}' +
  ']';
const myObj = JSON.parse(myJSON);
var regions = document.getElementById("m_continent");
regions.innerHTML = " <option value='-1'>اختر منطقة التوصيل</option>";

// 初始化区域下拉框(优化后用区域名称作为value)
Object.keys(myObj).forEach(function(key) {
  var regionName = Object.getOwnPropertyNames(myObj[key])[0];
  regions.innerHTML += "<option value=\"" + regionName + "\">" + regionName + "</option>";
});

function fillCities(val) {
  if (val === "-1") return;
  var cities = document.getElementById("m_cities");
  cities.innerHTML = " <option value='0'>اختر مدينة التوصيل</option>";
  
  // 找到选中区域对应的对象
  var regionObj = myObj.find(item => Object.keys(item)[0] === val);
  var allCities = Object.values(regionObj)[0];
  
  console.log("城市数组长度:", allCities.length); // 现在能正常获取长度

  for (var i = 0; i < allCities.length; i++) {
    var city = allCities[i];
    cities.innerHTML += "<option value=\"" + city.cityName + "\">" + city.cityName + "</option>";
  }
}

HTML代码

<!DOCTYPE html>
<html>
<body style="direction:rtl">
  <h2>مدن وأوقات التوصيل</h2>
  <p>يمكنك تقدير وقت وصول طلبك لمدينتك</p>
  <label for="m_continent">اختر منطقتك</label>
  <select id="m_continent" onchange="fillCities(this.value)">
  </select>
  <br>
  <label for="m_cities">اختر مدينتك</label>
  <select id="m_cities">
    <option value="0">اختر المنطقة أولا</option>
  </select>
  <p id="delivery-time"></p>
</body>
</html>

内容的提问来源于stack exchange,提问作者Sabbah

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.25 23:33:30