一、三对角矩阵

1.三对角矩阵概念

2.三对角矩阵元素数量

对于给定n阶方阵M,若其为三对角矩阵,则元素个数N为:

  • n=1,此时方阵只有一个元素M[0][0],由定义知该元素也在三对角线上。故N=1
  • n>1,由三对角矩阵特点知,矩阵的第一行和最后一行(第n行)分别有两个非零元素,其余行每行各有三个非零元素。故N = 3*(n-2)+2*2 = 3n-2

综上,
N = { 1 , n=1 3 n − 2 , n>1 N=\left\{ \begin{aligned} & 1 ,&\text{n=1}\\ & 3n-2, &\text{n>1}\\ \end{aligned} \right. N={​1,3n−2,​n=1n>1​

3.三对角矩阵下标变换推导(行优先和列优先)

对于给定n阶三对角方阵M和存放该方阵的数组A,非零元素M_ij1≤i,j≤n|i-j|≤1)同数组元素A[k]0≤k<N)存在一一对应的关系。下面分别推导从下标i,jkki,j的关系。

3.1行优先

  1. M_ijA[k]:即已知i,j要找出对应的k,需要知道,在数组A中,元素M_ij之前存放的元素个数num,则M_ij存放在A的第num+1个位置,对应数组A的下标正好为num(假设数组下标从0开始)。
  • 先考虑i>1的情况,即寻找第一行以下的非零元素M_ij

    • 第一行有2个非零元素;之后的2~i-1行,每行有三个非零元素。

    • i行,在M_ij之前的非零元素有j-(i-1)个。

k = num = 2+3*(i-1-1)+j-(i-1)=2i+j-3

  • 而当i=1时,有j=1或2。且A[0]=M_11,A[1]=M_12。代入发现也符合上述公式。
  1. A[k]M_ij

首先求出A[k]位于M的第几行:由于M的第一行有两个元素,2~i-1行有三个元素,由此可以得到i关于k的表达式:i = ⌊(k+1)/3+1⌋(下取整)。(i+1为第一行“补”一个元素,加一是因为i从1开始)。
然后可以根据上面得到的ki,j的关系得到:j = k-2i+3

3.列优先

由于三对角矩阵具有良好的对称性,所以只需要对行优先推导得到的关系中i,j互换即可。
即:

  • k=2j+i-3
  • j=⌊(k+1)/3+1⌋(下取整)i=k-2j+3

二、C++实现三对角矩阵代码

//diagonalMatrix.hpp
#pragma once
#include "assert.h"
#include <iostream>
template <typename E>
// 检查下标越界
#define CHECK(i, j) \assert(i >= 1 && j >= 1 && i <= m_dimension && j <= m_dimension);// 检查是否是对角阵中的非零元素
#define IS_ZERO(i, j) abs(i - j) > 1// 根据行/列优先原则获取数组对应下标
#define GET_IDX(i, j) m_priority ? (2 * i + j - 3) : (2 * j + i - 3)class DiagonalMatrix
{private:int m_dimension; // 方阵阶数int m_capacity;  // 数组容量,即方阵中非零元素数量E *m_array;      // 存储方阵的数组bool m_priority; // 0: 行优先 1:列优先
public:DiagonalMatrix(int dimension, bool priority = false) : m_dimension(dimension), m_priority(priority){assert(dimension >= 1);if (dimension == 1)m_capacity = 1;elsem_capacity = 3 * dimension - 2; // capacity = (d - 2)*3 + 2*2 = 3d -2m_array = new E[m_capacity];}~DiagonalMatrix(){delete m_array;m_array = nullptr;}// 设置元素M_ijvoid set(const E &element, int i, int j){CHECK(i, j);if (IS_ZERO(i, j))return;m_array[GET_IDX(i, j)] = element;}// 获取元素M_ijE get(int i, int j){CHECK(i, j);if (IS_ZERO(i, j))return 0;return m_array[GET_IDX(i, j)];}// 获取数组元素A[k]对应方阵的下标i和jvoid getKIdx(int k, int &i, int &j){assert(k >= 0 && k < m_capacity);if (!m_priority){i = (k + 1) / 3 + 1;j = k - 2 * i + 3;}else{j = (k + 1) / 3 + 1;i = k - 2 * j + 3;}}// 打印方阵void printMatrix(){for (int i = 1; i <= m_dimension; i++){for (int j = 1; j <= m_dimension; j++)std::cout << get(i, j) << ' ';std::cout << '\n';}}int getCapacity(){return m_capacity;}int getDimension(){return m_dimension;}
};

使用:

#include "diagonalMatrix.hpp"
int main()
{using namespace std;DiagonalMatrix<int> d(6);int matrix[6][6] ={{1, 1, 0, 0, 0, 0},{1, 1, 1, 0, 0, 0},{0, 1, 1, 1, 0, 0},{0, 0, 1, 1, 1, 0},{0, 0, 0, 1, 1, 1},{0, 0, 0, 0, 1, 1}};// set valueint i, j, k;for (i = 0; i < 6; i++)for (j = 0; j < 6; j++)if (matrix[i][j] != 0)d.set(matrix[i][j], i + 1, j + 1);// get idx and valuefor (k = 0; k < d.getCapacity(); k++){d.getKIdx(k, i, j);printf("k = %d , i = %d, j = %d , matrix[%d][%d] = %d\n", k, i, j, i, j, d.get(i, j));}d.printMatrix();
}

结果:

k = 0 , i = 1, j = 1 , matrix[1][1] = 1
k = 1 , i = 1, j = 2 , matrix[1][2] = 1
k = 2 , i = 2, j = 1 , matrix[2][1] = 1
k = 3 , i = 2, j = 2 , matrix[2][2] = 1
k = 4 , i = 2, j = 3 , matrix[2][3] = 1
k = 5 , i = 3, j = 2 , matrix[3][2] = 1
k = 6 , i = 3, j = 3 , matrix[3][3] = 1
k = 7 , i = 3, j = 4 , matrix[3][4] = 1
k = 8 , i = 4, j = 3 , matrix[4][3] = 1
k = 9 , i = 4, j = 4 , matrix[4][4] = 1
k = 10 , i = 4, j = 5 , matrix[4][5] = 1
k = 11 , i = 5, j = 4 , matrix[5][4] = 1
k = 12 , i = 5, j = 5 , matrix[5][5] = 1
k = 13 , i = 5, j = 6 , matrix[5][6] = 1
k = 14 , i = 6, j = 5 , matrix[6][5] = 1
k = 15 , i = 6, j = 6 , matrix[6][6] = 1
1 1 0 0 0 0
1 1 1 0 0 0
0 1 1 1 0 0
0 0 1 1 1 0
0 0 0 1 1 1
0 0 0 0 1 1

三对角矩阵原理及C++实现相关推荐

  1. G-S迭代求解线性方程,以及三对角矩阵求解

    G-S迭代 代码最少可以这么写: def GS(A,b,X,N):X_old = X.copy()n = X.shape[0]for k in range(N):X[0,0] = (b[0,0] - ...

  2. python生成任意n阶的三对角矩阵

    数学作业要求实现共轭梯度法的算法. 题目中的矩阵A是n=400/500/600的三对角矩阵. 在网上查阅资料未果后,自己解决了. import numpy as npdef generate_matr ...

  3. 对称矩阵到三对角矩阵的Lanczos推导(python,数值积分)

    第三十二篇 Lanczos转化到三对角形式 在之前的篇章里,有许多求解线性方程的迭代方法,如最陡下降法,可以通过向量乘法和各种简单的向量运算,简化为一个单个矩阵的循环.将矩阵化为三对角形式的Lancz ...

  4. 一维数组二维数组对称矩阵三角矩阵三对角矩阵地址的计算

    一维数组的地址计算 设每个元素的大小是size,首元素的地址是a[1],则 a[i] = a[1] + (i-1)*size 若首元素的地址是a[0] 则a[i] = a[0] + i*size 二维 ...

  5. 数据结构-特殊矩阵【对称矩阵、上三角下三角矩阵、三对角矩阵】的压缩存储代码实现

    #include <iostream> using namespace std;typedef int ElemType;void SymmetricMatrixStore(int n, ...

  6. 20180316 三对角矩阵

    将一个A[1..100,1..100]的三对角矩阵,按行优先存入一维数组B[1..298]中,A中元素A6665 (即该元素下标i=66,j=65),在B数组中的位置K为()供选择的答案: 198 1 ...

  7. 为什么次对角线元素均不为零的三对角矩阵为不可约矩阵

    不可约矩阵的定义及判定方法可见:参考 这里,我们从有向图的角度来进行证明. 因为我们讨论的是次对角线元素均不为零的三对角矩阵,所以我们可以得到aij≠0,aji≠0,i≠ja_{ij}\ne0,a_{ ...

  8. 数据结构与算法-三对角矩阵的压缩公式推导

    数据结构与算法-三对角矩阵的压缩公式推导 三对角矩阵 压缩公式推导 (1)考虑a[i,j]处在第2到第n-1行之间: 我们可以看到,从第二行开始,元素的个数都为3个.对于a[i,j]将要存储的数组下标 ...

  9. 数据结构-拓展突破-特殊矩阵(对称矩阵,三角矩阵,三对角矩阵,稀疏矩阵)的压缩存储)

    文章目录 1. 对称矩阵 2. 三角矩阵 3. 三对角矩阵 4. 稀疏矩阵 1. 对称矩阵 对称矩阵的定义: 若n阶方阵中任意一个元素a,都有a(i,j)=a(j,i)则该矩阵为对称矩阵 也就是说对称 ...

最新文章

  1. C#设置当前程序通过IE代理服务器上网
  2. CSharpGL(5)解析3DS文件并用CSharpGL渲染
  3. oracle文件大小的限制
  4. Android -- DragDrop
  5. WINDOWS XP SP2 NTFS EFS加密文件的解密案例
  6. 前端学习(534):多列布局1
  7. java 文件下载,中文表名,中文内容
  8. python训练模型测试模型_python 机器学习中模型评估和调参
  9. Xcode中常见的错误,警告和解决方法
  10. 五种最常见的开源路由器第三方固件测评-转
  11. DHCP中继原理和配置(含常见配置配置误区)
  12. 免费 web api 接口大全
  13. # 图书管理系统案例练习
  14. 机器学习、数据挖掘、神经网络、人工智能和模式识别之间,主要是什么关系
  15. cent7 安装 notepadqq
  16. 解读| 支付宝催泪视频背后的反欺诈升级战
  17. ERROR: Failed to parse XML in E:\LWJ\AndroidStudioProjects\MyApplication6\app\src\main\AndroidManife
  18. 母牛的故事——无脑模拟解法
  19. 微信小程序跳过第三方的_微信小程序怎么解除第三方授权?
  20. MA、WMA、EMA、EXPMA区别及公式详述

热门文章

  1. 宣传片制作,你不知道的重点有哪些
  2. c语言 手机app防沉迷系统,推荐 | 那些手机防沉迷的APP
  3. 图片浏览插件(支持图片轮播、上下张查看、放大缩小、旋转)
  4. 如何彻底关闭win10实时防护以及解决无法找到gpedit.msc的问题
  5. 如何借电子印章助力印章管理安全高效?
  6. 抖音运营干货:抖音橱窗、抖音购物车、抖音小店、抖音直播的区别
  7. OneNote快捷键
  8. python父亲节礼物_父亲节礼物篇——父亲节适合父亲的礼物良心推荐
  9. Java 黄金贵金属理财投资系统源码发布
  10. python怎么快速打括号_中括号怎么打-【python每日一练】有效括号