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

如何删除数组冗余行并避免报错:Cannot read properties of undefined (reading 'label')

问题分析与解决办法

先说说你遇到的两个错误原因

1. 「Cannot read properties of undefined (reading 'label')」

第二个for循环是照着options的长度(2次)遍历的,但删完冗余元素后optionsThree只剩1个元素,循环到第2次时optionsThree[1]不存在,访问option3.label自然就报错了。

2. 「Encountered two children with the same key」

两个循环都用i作为组件的key,第一个循环生成key=0、1,第二个循环也生成0、1,React要求列表子元素的key必须唯一,这不就冲突了嘛。

修复错误的基础版代码

先把循环逻辑和key的问题解决,同时加存在判断避免取undefined:

const rows: JSX.Element[] = [];

// 处理前两行的左右Radio
for (let i = 0; i < options.length; i += 1) {
    const option1 = options[i];
    const option2 = optionsTwo[i];

    rows.push(
        <View key={`pair-${i}`}>
            <View style={{ flexDirection: "row" }}>
                {/* 加存在判断,避免意外报错 */}
                {option1 && (
                    <Radio
                        onPress={() => onChange(option1.value)}
                        label={option1.label}
                        checked={option1.value === value}
                        style={{ flex: 1 }}
                    />
                )}
                {option2 && (
                    <Radio
                        onPress={() => onChange(option2.value)}
                        label={option2.label}
                        checked={option2.value === value}
                        style={{ flex: 1}}
                    />
                )}
            </View>
        </View>
    );
}

// 处理第三组的单行Radio,循环optionsThree自身的长度
for (let i = 0; i < optionsThree.length; i += 1) {
    const option3 = optionsThree[i];
    // 不存在直接跳过
    if (!option3) continue;

    rows.push(
        <View key={`single-${i}`}>
            <View style={{ flexDirection: "row" }}>
                <Radio
                    onPress={() => onChange(option3.value)}
                    label={option3.label}
                    checked={option3.value === value}
                    style={{ flex: 1 }}
                />
                <View style={{ flex: 1}} />
            </View>
        </View>
    );
}

return (
    <View>
        <View>{rows}</View>
    </View>
);

对应的选项数组用你修改后的版本:

options={[
    { label: "label", value: "value" },
    { label: "label", value: "value3" },
]}
optionsTwo={[
    { label: "label", value: "value2" },
    { label: "label", value: "value4" },
    { label: "label", value: "value7" },
]}
optionsThree={[
    { label: "label", value: "value11" },
    // 冗余元素已删除
]}

更省心的优化方案(推荐)

如果后续要加行或调整布局,建议用统一配置的方式,把每行的左右内容明确定义,维护起来更方便:

// 直接定义每一行的左右内容,一目了然
const rowConfigs = [
    { left: options[0], right: optionsTwo[0] },
    { left: options[1], right: optionsTwo[1] },
    { left: optionsThree[0], right: null }, // 右侧留空占位
];

// 用map生成所有行,key绝对不会重复
const rows = rowConfigs.map((config, index) => (
    <View key={`row-${index}`}>
        <View style={{ flexDirection: "row" }}>
            {config.left && (
                <Radio
                    onPress={() => onChange(config.left.value)}
                    label={config.left.label}
                    checked={config.left.value === value}
                    style={{ flex: 1 }}
                />
            )}
            {/* 右侧有内容就放Radio,没有就放占位View */}
            {config.right ? (
                <Radio
                    onPress={() => onChange(config.right.value)}
                    label={config.right.label}
                    checked={config.right.value === value}
                    style={{ flex: 1}}
                />
            ) : (
                <View style={{ flex: 1}} />
            )}
        </View>
    </View>
));

return (
    <View>
        <View>{rows}</View>
    </View>
);

这种方式把布局逻辑和数据解耦,新增或修改行只需要调整rowConfigs,不用动循环代码,可读性和维护性更强。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.20 17:42:15