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

面向对象架构中,能否将数组传入多个类?求最佳实践

面向对象架构优化方案建议

针对你遇到的上帝类、贫血领域模式及类命名问题,以下是贴合OOP最佳实践的优化思路:

1. 拆分职责:区分领域实体、集合类与服务类

  • 领域实体类(名词):定义Journey类,封装单个学习旅程的属性和自身专属行为,比如验证数据合法性的validate()、更新完成状态的markAsCompleted()、累加学习时长的addLearningHours()等,让实体拥有自主行为,避免沦为单纯的属性容器。
  • 集合类(名词):保留JourneyCollection但收缩职责,仅负责Journey对象的集合管理——比如添加/移除实体、基础的筛选排序,复杂逻辑可委托给专门类处理,不包揽所有业务。
  • 服务类(名词):如果存在跨实体或非核心业务逻辑(比如批量导入、本地存储交互),单独创建JourneyStorage、JourneyReportService这类服务类,专注单一功能。

2. 规避上帝类的具体操作

  • 拆分原JourneyCollection中的非集合逻辑:将数据持久化(如前端本地存储)交给JourneyStorage类;把复杂筛选规则拆成JourneySubjectFilter、JourneyCompletionFilter等专用过滤器,由JourneyCollection调用而非自行实现。
  • 严格遵循单一职责原则:每个类只负责一件事,比如JourneyCollection仅维护集合的完整性和基础操作,筛选排序的具体规则由过滤器类完成。

3. 避免贫血领域模式的关键

  • 不让Journey类只存属性:所有涉及单个旅程的状态变更、数据校验都封装在Journey内部,外部只能通过调用它的方法修改状态,比如用addLearningHours(5)替代直接修改journey.hours +=5,同时在方法内做合法性校验(如时长不能为负)。
  • 集合类操作依赖实体方法:比如JourneyCollection的addJourney()方法会先调用journey.validate(),确保数据合法后再加入集合,而非直接操作实体属性。

4. 类命名原则的重要性

  • 类是对事物的抽象,用名词命名能清晰体现其代表的实体或服务,契合OOP封装数据与行为的核心思想。动词命名的类本质是函数的包装,违背了类的设计初衷,会让代码结构混乱、难以维护。
  • 示例:用JourneyCollection.addJourney(journey)替代单独的AddJourney类,或让JourneyService.createAndAddJourney(data)完成创建+添加的组合操作,语义更符合OOP逻辑。

示例代码片段

// 领域实体类:Journey
class Journey {
  constructor(subject, startDate, hours = 0) {
    this.subject = subject;
    this.startDate = startDate;
    this.hours = hours;
    this.completed = false;
  }

  validate() {
    if (!this.subject || !this.startDate) throw new Error("必填字段缺失");
    if (this.hours < 0) throw new Error("学习时长不能为负数");
  }

  markAsCompleted() {
    this.completed = true;
  }

  addLearningHours(hours) {
    if (hours > 0) this.hours += hours;
  }
}

// 集合类:JourneyCollection
class JourneyCollection {
  constructor() {
    this.journeys = [];
  }

  addJourney(journey) {
    journey.validate();
    this.journeys.push(journey);
  }

  filterBySubject(subject) {
    return this.journeys.filter(j => j.subject === subject);
  }

  sortByStartDate(ascending = true) {
    return [...this.journeys].sort((a, b) => {
      const dateA = new Date(a.startDate);
      const dateB = new Date(b.startDate);
      return ascending ? dateA - dateB : dateB - dateA;
    });
  }
}

// 服务类:JourneyStorage(负责本地存储)
class JourneyStorage {
  saveCollection(collection) {
    localStorage.setItem('journeys', JSON.stringify(collection.journeys));
  }

  loadCollection() {
    const data = localStorage.getItem('journeys');
    const collection = new JourneyCollection();
    if (data) {
      JSON.parse(data).forEach(item => {
        const journey = new Journey(item.subject, item.startDate, item.hours);
        journey.completed = item.completed;
        collection.addJourney(journey);
      });
    }
    return collection;
  }
}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.19 15:45:41