302
社区成员
发帖
与我相关
我的任务
分享| 类名 | 代码行数 | 属性个数 | 方法个数 | 总代码规模 |
|---|---|---|---|---|
| Expression | 418 | 1 (monomials) | 18 | 较大 |
| Expression.Monomial | 143 (内部类) | 4 (coeff, xexp, yexp, expExpr) | 10 | 中等 |
| Parser | ~230 | 3 (tokenizer, curToken, funcEnv) | 12 | 较大 |
| DerivativeFactor | ~130 | 2 (expr, variable) | 5 | 中等 |
| FuncEnv | ~127 | 6 (hasFunc, defExpr, hasRecursiveFunc, f0Expr, f1Expr, recursiveDef) | 7 | 中等 |
| Main | ~160 | 0 | 4 | 中等 |
| 其他Factor类 | 平均~50 | 平均2-3 | 平均2-3 | 较小 |
Expression类关键方法:
| 方法名 | 代码行数 | 控制分支数 | 圈复杂度 | 评价 |
|---|---|---|---|---|
toNecessaryBracketString() | 11 (重构后) | 2 | 低 | 良好,已拆分 |
appendMonomial() | 10 | 1 | 低 | 良好 |
mergeLikeTerms() | 39 | 4 | 中 | 可接受 |
multiplyExpr() | 23 | 3 | 中 | 可接受 |
replaceVar() | 30 | 4 | 中 | 可接受 |
Parser类关键方法:
| 方法名 | 代码行数 | 控制分支数 | 圈复杂度 | 评价 |
|---|---|---|---|---|
parseExpression() | 15 | 2 | 低 | 良好 |
parseFactor() | 25 | 10 | 高 | 需要关注,使用了switch-case |
parseTermExpr() | 12 | 2 | 低 | 良好 |
DerivativeFactor类关键方法:
| 方法名 | 代码行数 | 控制分支数 | 圈复杂度 | 评价 |
|---|---|---|---|---|
differentiateMonomial() | 24 (重构后) | 3 | 中 | 良好,已拆分 |
differentiateVarAndExp() | 40 | 4 | 中 | 可接受 |
differentiateVar() | 23 | 3 | 中 | 可接受 |
内聚性分析:
耦合性分析:
设计模式应用:
┌─────────────────────────────────────────────────────────────┐
│ Factor (抽象) │
│ + asExpression() │
└─────────────────────────────────────────────────────────────┘
△
┌──────────────────┼──────────────────┐
│ │ │
┌─────────┴─────┐ ┌─────────┴─────┐ ┌─────────┴─────┐
│ ConstFactor │ │VariableFactor │ │ ExprFactor │
│ - value │ │ - var │ │ - expr │
│ - exponent │ │ - exponent │ │ - exponent │
└───────────────┘ └───────────────┘ └───────────────┘
│
│ ┌───────────────┐ ┌───────────────┐
│ │ ExpFactor │ │ FuncCallFactor│
│ │ - parameter │ │ - actual │
│ │ - exponent │ │ - funcEnv │
│ └───────────────┘ └───────────────┘
│
│ ┌───────────────┐ ┌───────────────┐
└─────────▶│DerivativeFactor│ │ ChoiceFactor │
│ - expr │ │ - cond... │
│ - variable │ │ - ifTrue │
└───────────────┘ │ - ifFalse │
└───────────────┘
┌─────────────────────────────────────────────────────────────┐
│ Expression │
│ - monomials: List<Monomial> │
│ + addExpr() + multiplyExpr() + mergeLikeTerms() │
│ + replaceVar() + toNecessaryBracketString() │
├─────────────────────────────────────────────────────────────┤
│ ┌───────────────────────────────────────────────────────┐ │
│ │ Monomial │ │
│ │ - coeff, xexp, yexp, expExpr │ │
│ │ + equals() + hashCode() + toString() │ │
│ └───────────────────────────────────────────────────────┘ │
└─────────────────────────────────────────────────────────────┘
┌─────────────────────────────────────────────────────────────┐
│ Parser │
│ - tokenizer, curToken, funcEnv │
│ + parseExpression() + parseFactor() + parseTerm() │
└─────────────────────────────────────────────────────────────┘
┌─────────────────────────────────────────────────────────────┐
│ FuncEnv │
│ - hasFunc, defExpr, hasRecursiveFunc │
│ - f0Expr, f1Expr, recursiveDef │
│ + getRecursiveFuncValue() │
└─────────────────────────────────────────────────────────────┘
1. Factor层次结构
2. Expression与Monomial组合
3. Parser职责分离
4. FuncEnv管理函数定义
优点:
缺点:
第一次作业(基础表达式展开):
第二次作业(添加函数和指数):
第三次作业(添加递推和求导):
重构前的问题:
toNecessaryBracketString() 方法过长(~70行)parseRecursiveDef() 方法过长(~70行)differentiateMonomial() 方法过长(~65行)xExp应为xExponent)重构后的改进:
toNecessaryBracketString()拆分为6个小方法parseRecursiveDef()拆分为4个辅助方法differentiateMonomial()拆分为3个专用方法重构体验:
假设新迭代:添加三角函数sin/cos
可扩展性分析:
优势:
Bug 1:递推函数系数提取错误
f{n}(x)= 1 *f{n-1}(x) + 2 * f{n-2}(x) 计算结果错误parseRecursiveDef()方法Bug 2:变量替换不完全
f{3}((x+y)) 展开后仍包含x而非(x+y)getRecursiveFuncValue()方法Bug 3:exp表达式括号不匹配
exp((x)缺少右括号toNecessaryBracketString()方法| 方法 | 代码行 | 圈复杂度 | 是否出Bug | 分析 |
|---|---|---|---|---|
parseRecursiveDef() | 70→30 | 高→中 | 是 | 复杂度高导致逻辑错误 |
getRecursiveFuncValue() | 25 | 中 | 是 | 递归逻辑复杂 |
toNecessaryBracketString() | 70→11 | 高→低 | 是 | 重构后修复 |
parseFactor() | 25 | 高 | 否 | 虽然复杂但逻辑清晰 |
mergeLikeTerms() | 39 | 中 | 否 | 逻辑稳定 |
结论: 方法复杂度与Bug发生率正相关,重构拆分方法能有效减少Bug。
1. 单元测试
2. 集成测试
3. 边界测试
4. 随机测试
1. 方法拆分
2. 命名规范
3. 表达式化简
1. 缓存机制
2. 并行计算
3. 表达式简化
1. 代码生成
2. Bug定位
3. 重构建议
4. 文档撰写
观察到的现象:
判断依据:
1. 面向对象设计
2. 递归与迭代
3. 代码质量
4. 测试驱动
1. 增加前置知识
2. 强化测试环节
3. 代码评审环节
4. 迭代式开发
第一单元的学习让我深刻体会到了良好架构设计的重要性。通过三次作业的迭代,我逐步构建了一个可扩展、易维护的表达式处理系统。虽然在过程中遇到了不少Bug和挑战,但正是这些问题让我学会了如何通过度量分析代码质量、如何进行有效的重构、如何设计全面的测试用例。
面向对象编程不仅仅是语法的使用,更是一种思维方式。通过合理的类设计和职责划分,我们可以构建出既满足当前需求又易于未来扩展的系统。这对我今后的软件开发生涯将产生深远的影响。