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

JS OOP中Ship类构造函数调用addShip报错求助

解决Ship构造函数调用addShip时的TypeError问题

问题根源

你已经准确定位了报错原因:测试代码创建Itinerary时传入了二维数组[[port]],导致itinerary.ports成为嵌套数组,itinerary.ports[0]实际是一个数组而非Port类实例。数组没有addShip方法,因此调用this.currentPort.addShip(this)时抛出TypeError。

解决方案

1. 修复测试代码的数组传入错误

将测试中Itinerary的参数从二维数组改为一维数组,确保itinerary.ports直接存放Port实例:

describe("Ship", () => {
  it('can be instantiated', () => {
      const port = new Port ('Dover');
      const itinerary = new Itinerary([port]) // 移除嵌套的外层数组
      const ship = new Ship(itinerary)
      expect(ship).toBeInstanceOf(Object)
  })
})

修改后itinerary.ports[0]将正确指向Port实例,addShip方法可正常执行,测试即可通过。

2. 给Ship类添加防御性校验(可选但推荐)

为避免后续传入非法格式的Itinerary,可在Ship构造函数中增加合法性校验,提前拦截错误:

class Ship{
    constructor(itinerary){
        // 校验行程及港口的合法性
        if (!itinerary?.ports?.length || !(itinerary.ports[0] instanceof Port)) {
            throw new Error('无效行程:必须包含至少一个Port实例');
        }
        
        this.itinerary = itinerary;
        this.currentPort = itinerary.ports[0];
        this.previousPort = null;
        this.currentPort.addShip(this);
    }

    // 原setSail、dock方法保持不变
}

后续若再传入错误格式的行程,会直接抛出明确的错误提示,便于快速排查问题。

额外优化:修复Port类的removeShip方法

注意到Port类的removeShip方法存在逻辑错误:pop()方法不接受参数,只会删除数组最后一个元素,无法移除指定船舶。建议修改为:

class Port {
    // 原构造函数、addShip方法保持不变

    removeShip(ship){
        if(ship){
            // 过滤掉目标船舶,返回新数组
            this.ships = this.ships.filter(s => s !== ship);
            // 或用splice实现:
            // const shipIndex = this.ships.indexOf(ship);
            // if (shipIndex !== -1) this.ships.splice(shipIndex, 1);
        }   
    }
}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.12 13:10:27