HarmonyOS鸿蒙Next数学类上架项目解析6-矩阵行列式计算
HarmonyOS鸿蒙Next数学类上架项目解析6-矩阵行列式计算 在开发鸿蒙数学计算应用时,需要实现矩阵行列式的计算功能。要求:
- 支持任意n阶方阵的行列式计算
- 使用递归展开法(拉普拉斯展开)
- 对于小阶矩阵使用直接公式优化性能
如何用ArkTS实现一个矩阵行列式计算器?
行列式是方阵的一个重要数值特征,计算方法主要有:
- 2阶:|A| = a₁₁a₂₂ - a₁₂a₂₁
- 3阶:萨鲁斯法则(对角线法则)
- n阶:拉普拉斯展开(按某行/列展开)
拉普拉斯展开公式:det(A) = Σ aᵢⱼ × (-1)^(i+j) × Mᵢⱼ
1. 定义数据模型
// 矩阵类型
type Matrix = number[][]
// 计算结果接口
interface DeterminantResult {
value: number // 行列式值
size: number // 矩阵阶数
isValid: boolean // 是否有效
errorMsg?: string // 错误信息
}
2. 核心计算函数
验证是否为有效方阵
@param matrix 输入矩阵
@returns 是否有效
function isValidSquareMatrix(matrix: Matrix): boolean {
if (!matrix || matrix.length === 0) {
return false
}
const n: number = matrix.length
for (let i = 0; i < n; i++) {
if (!matrix[i] || matrix[i].length !== n) {
return false
}
}
return true
}
获取余子式矩阵(删除第row行第col列)
@param matrix 原矩阵
@param row 删除的行
@param col 删除的列
@returns 余子式矩阵
function getMinorMatrix(matrix: Matrix, row: number, col: number): Matrix {
const n: number = matrix.length
const minor: Matrix = []
for (let i = 0; i < n; i++) {
if (i === row) continue
const newRow: number[] = []
for (let j = 0; j < n; j++) {
if (j === col) continue
newRow.push(matrix[i][j])
}
minor.push(newRow)
}
return minor
}
计算2阶行列式
function det2x2(matrix: Matrix): number {
return matrix[0][0] * matrix[1][1] - matrix[0][1] * matrix[1][0]
}
计算3阶行列式(萨鲁斯法则)
function det3x3(matrix: Matrix): number {
const a = matrix
return (
a[0][0] * a[1][1] * a[2][2] +
a[0][1] * a[1][2] * a[2][0] +
a[0][2] * a[1][0] * a[2][1] -
a[0][2] * a[1][1] * a[2][0] -
a[0][1] * a[1][0] * a[2][2] -
a[0][0] * a[1][2] * a[2][1]
)
}
递归计算n阶行列式(拉普拉斯展开)
@param matrix 方阵
@returns 行列式值
function determinant(matrix: Matrix): number {
const n: number = matrix.length
// 1阶矩阵
if (n === 1) {
return matrix[0][0]
}
// 2阶矩阵直接计算
if (n === 2) {
return det2x2(matrix)
}
// 3阶矩阵使用萨鲁斯法则
if (n === 3) {
return det3x3(matrix)
}
// n阶矩阵使用拉普拉斯展开(按第一行展开)
let det: number = 0
for (let j = 0; j < n; j++) {
const sign: number = Math.pow(-1, j)
const minor: Matrix = getMinorMatrix(matrix, 0, j)
det += sign * matrix[0][j] * determinant(minor)
}
return det
}
计算矩阵行列式(带验证)
@param matrix 输入矩阵
@returns 计算结果
function calculateDeterminant(matrix: Matrix): DeterminantResult {
// 验证输入
if (!isValidSquareMatrix(matrix)) {
return {
value: 0,
size: 0,
isValid: false,
errorMsg: '请输入有效的方阵'
}
}
const n: number = matrix.length
// 检查是否包含无效数值
for (let i = 0; i < n; i++) {
for (let j = 0; j < n; j++) {
if (Number.isNaN(matrix[i][j]) || !Number.isFinite(matrix[i][j])) {
return {
value: 0,
size: n,
isValid: false,
errorMsg: '矩阵包含无效数值'
}
}
}
}
try {
const det: number = determinant(matrix)
return {
value: det,
size: n,
isValid: true
}
} catch (error) {
return {
value: 0,
size: n,
isValid: false,
errorMsg: '计算过程出错'
}
}
}
3. 矩阵输入解析
从字符串解析矩阵
格式:每行用分号分隔,每个元素用逗号分隔
例如:"1,2,3;4,5,6;7,8,9"
function parseMatrix(input: string): Matrix | null {
try {
const rows: string[] = input.trim().split(';')
const matrix: Matrix = []
for (const row of rows) {
const elements: number[] = row.split(',').map(s => parseFloat(s.trim()))
if (elements.some(e => Number.isNaN(e))) {
return null
}
matrix.push(elements)
}
return matrix
} catch (error) {
return null
}
}
矩阵转字符串显示
function matrixToString(matrix: Matrix): string {
return matrix.map(row => row.join('\t')).join('\n')
}
4. 完整UI组件实现
@Entry
@Component
struct DeterminantCalculator {
@State matrixSize: number = 3
@State matrixInput: string = '1,2,3;4,5,6;7,8,9'
@State result: DeterminantResult | null = null
@State parsedMatrix: Matrix | null = null
build() {
Column() {
Text('矩阵行列式计算器')
.fontSize(24)
.fontWeight(FontWeight.Bold)
.margin({ bottom: 10 })
Text('拉普拉斯展开法')
.fontSize(14)
.fontColor('#666666')
.margin({ bottom: 20 })
// 矩阵阶数选择
Row() {
Text('矩阵阶数:')
Button('2×2').onClick(() => this.setMatrixSize(2))
.backgroundColor(this.matrixSize === 2 ? '#007AFF' : '#E0E0E0')
.margin({ right: 8 })
Button('3×3').onClick(() => this.setMatrixSize(3))
.backgroundColor(this.matrixSize === 3 ? '#007AFF' : '#E0E0E0')
.margin({ right: 8 })
Button('4×4').onClick(() => this.setMatrixSize(4))
.backgroundColor(this.matrixSize === 4 ? '#007AFF' : '#E0E0E0')
}
.margin({ bottom: 15 })
// 矩阵输入
Text('输入矩阵(行用分号分隔,元素用逗号分隔):')
.fontSize(14)
.margin({ bottom: 8 })
TextArea({ text: this.matrixInput })
.width('100%')
.height(100)
.onChange((value: string) => {
this.matrixInput = value
this.parsedMatrix = parseMatrix(value)
})
.margin({ bottom: 10 })
// 矩阵预览
if (this.parsedMatrix) {
Column() {
Text('矩阵预览:')
.fontSize(14)
.margin({ bottom: 8 })
Text(matrixToString(this.parsedMatrix))
.fontFamily('monospace')
.fontSize(16)
}
.padding(12)
.backgroundColor('#f0f0f0')
.borderRadius(8)
.margin({ bottom: 15 })
}
// 计算按钮
Button('计算行列式')
.onClick(() => this.handleCalculate())
.width(200)
.margin({ bottom: 20 })
// 结果显示
if (this.result) {
Column() {
if (this.result.isValid) {
Text(`${this.result.size}阶矩阵行列式:`)
.fontSize(16)
.margin({ bottom: 8 })
Text(`det(A) = ${this.result.value}`)
.fontSize(24)
.fontWeight(FontWeight.Bold)
.fontColor('#007AFF')
} else {
Text(this.result.errorMsg || '计算错误')
.fontColor(Color.Red)
}
}
.padding(16)
.backgroundColor('#f5f5f5')
.borderRadius(8)
}
}
.width('100%')
.height('100%')
.padding(20)
}
setMatrixSize(size: number): void {
this.matrixSize = size
// 生成示例矩阵
const examples: Map<number, string> = new Map([
[2, '1,2;3,4'],
[3, '1,2,3;4,5,6;7,8,9'],
[4, '1,2,3,4;5,6,7,8;9,10,11,12;13,14,15,16']
])
this.matrixInput = examples.get(size) || ''
this.parsedMatrix = parseMatrix(this.matrixInput)
}
handleCalculate(): void {
const matrix = parseMatrix(this.matrixInput)
if (matrix) {
this.result = calculateDeterminant(matrix)
} else {
this.result = {
value: 0,
size: 0,
isValid: false,
errorMsg: '矩阵格式错误'
}
}
}
}
5. 使用示例
// 示例1:2阶矩阵 // |1 2| // |3 4| = 1×4 - 2×3 = -2 const matrix2: Matrix = [[1, 2], [3, 4]] const result1 = calculateDeterminant(matrix2) // { value: -2, size: 2, isValid: true }
// 示例2:3阶矩阵 // |1 2 3| // |4 5 6| = 0(行列式为0,矩阵奇异) // |7 8 9| const matrix3: Matrix = [[1, 2, 3], [4, 5, 6], [7, 8, 9]] const result2 = calculateDeterminant(matrix3) // { value: 0, size: 3, isValid: true }
// 示例3:3阶单位矩阵 // |1 0 0| // |0 1 0| = 1 // |0 0 1| const identity: Matrix = [[1, 0, 0], [0, 1, 0], [0, 0, 1]] const result3 = calculateDeterminant(identity) // { value: 1, size: 3, isValid: true }
总结
使用ArkTS实现矩阵行列式计算的关键点:
- 对于2阶和3阶矩阵使用直接公式,效率更高
- n阶矩阵使用拉普拉斯展开,时间复杂度为O(n!)
- 递归计算时需要正确处理代数余子式的符号(-1)^(i+j)
- 行列式为0表示矩阵奇异(不可逆)
- 对于大型矩阵,可以考虑使用LU分解等更高效的算法
- 项目链接:https://gitee.com/solgull/math-fbox
更多关于HarmonyOS鸿蒙Next数学类上架项目解析6-矩阵行列式计算的实战系列教程也可以访问 https://www.itying.com/category-93-b0.html
鸿蒙Next数学类库提供Matrix类用于矩阵运算。行列式计算可通过Matrix.determinant()方法实现,该方法基于LU分解算法,支持2x2、3x3及更高阶方阵。调用时需确保矩阵为方阵,否则会抛出IllegalArgumentException异常。具体实现可参考HarmonyOS API文档中Matrix类的相关说明。
在HarmonyOS Next中使用ArkTS实现矩阵行列式计算器,可通过递归展开法结合小阶矩阵优化来实现。以下是核心实现方案:
1. 数据结构定义
class Matrix {
data: number[][];
constructor(data: number[][]) {
this.data = data;
}
}
2. 小阶矩阵优化计算
private determinant2x2(mat: Matrix): number {
return mat.data[0][0] * mat.data[1][1] - mat.data[0][1] * mat.data[1][0];
}
private determinant3x3(mat: Matrix): number {
const a = mat.data;
return a[0][0] * (a[1][1] * a[2][2] - a[1][2] * a[2][1])
- a[0][1] * (a[1][0] * a[2][2] - a[1][2] * a[2][0])
+ a[0][2] * (a[1][0] * a[2][1] - a[1][1] * a[2][0]);
}
3. 递归展开主函数
calculateDeterminant(mat: Matrix): number {
const n = mat.data.length;
// 小阶矩阵直接计算
if (n === 1) return mat.data[0][0];
if (n === 2) return this.determinant2x2(mat);
if (n === 3) return this.determinant3x3(mat);
let det = 0;
// 按第一行展开
for (let j = 0; j < n; j++) {
const subMatrix = this.getSubMatrix(mat, 0, j);
const sign = (j % 2 === 0) ? 1 : -1;
det += sign * mat.data[0][j] * this.calculateDeterminant(subMatrix);
}
return det;
}
4. 子矩阵生成函数
private getSubMatrix(mat: Matrix, row: number, col: number): Matrix {
const n = mat.data.length;
const subData: number[][] = [];
for (let i = 0; i < n; i++) {
if (i === row) continue;
const newRow: number[] = [];
for (let j = 0; j < n; j++) {
if (j === col) continue;
newRow.push(mat.data[i][j]);
}
subData.push(newRow);
}
return new Matrix(subData);
}
5. 性能优化建议
- 对于4阶及以下矩阵使用硬编码公式
- 添加矩阵奇异性检查,行列式为0时提前返回
- 可考虑使用LU分解法作为备选算法提升大矩阵性能
6. 使用示例
const matrix = new Matrix([
[1, 2, 3],
[4, 5, 6],
[7, 8, 9]
]);
const det = calculator.calculateDeterminant(matrix);
此实现通过递归展开满足n阶方阵计算需求,同时针对小阶矩阵优化避免了不必要的递归开销。

