目錄
導語
上三角矩陣就是一種對角線以下元素都爲0的 n x n矩陣。其中右上三角矩陣是指對角線以下的元素都爲0。
由於上三角矩陣仍然有大量元素爲0,爲了避免浪費太多的內存空間,可以把三角矩陣的二維模式存儲在一維列表中。
... | ||||
0 | ... | |||
0 | 0 | ... | ||
... | ... | ... | ... | ... |
0 | 0 | 0 | ... |
對於如上所示的 n x n右上三角矩陣A(ij),如果i > j,那麼對應位置的元素值爲0。
解決方案
由於採用Python解決這個問題,一維列表不需要實現聲明大小。將該矩陣的有效元素映射爲一維列表存儲有兩種解決方案,映射方式分爲以行爲主和以列爲主兩種方式。
1. 以行爲主的存儲映射
以行爲主的存儲方案是先將右上三角矩陣的第一行對角線及對角線以上的元素存儲在一維列表中,然後在將右上三角矩陣的第二行對角線及對角線以上的元素存儲在一維列表中。。。以此類推存儲每一行元素。這樣存儲的一維列表中包含了右上三角矩陣中全部的有效元素。
... | ... | ... |
觀察一維列表存儲的數據和座標之間的關係,第0個位置存儲,第1個位置存儲,... 第n-1個位置存儲。第n個位置存儲...
因此存儲在一維列表中的映射位置是
2. 以列爲主的存儲映射
以列爲主的存儲方案是先將右上三角矩陣的第一列對角線及對角線以上的元素存儲在一維列表中,然後在將右上三角矩陣的第二列對角線及對角線以上的元素存儲在一維列表中。。。以此類推存儲每一列元素。這樣存儲的一維列表中包含了右上三角矩陣中全部的有效元素。
存儲原理與上文類似,這裏直接給出映射關係:
無論選擇哪一種存儲映射,都可以將右上三角矩陣壓縮爲一個一維列表。本文選用以列爲主的存儲映射舉例說明。
示例題目
1. 題目描述
設計一個Python程序,輸入一個右上三角矩陣,輸出壓縮後的一維數組。
2. 輸入/輸出描述
輸入描述:
輸入右上三角矩陣的總行數、默認數字,然後自動計算大小,提示輸入對應的數字。
Input matrix rows: 1
Input default value: 0
upper_triangular_matrix[0][0]: 8
輸出描述:
輸出原右上三角矩陣和壓縮成一維列表後的矩陣。
------upper triangular matrix------
| 8 |
------compress upper triangular matrix --> list ------
[8]
3. 代碼
class MatrixException(Exception):
def __init__(self, message, code):
self.message = message
self.code = code
# 1. 輸入一個右上三角矩陣
try:
rows = int(input("Input matrix rows: "))
if rows <= 0:
raise MatrixException("Matrix rows can not less than zero.", 1002)
columns = rows
default_value = int(input("Input default value: "))
utm = [[default_value] * columns for row in range(rows)]
for row in range(rows):
for column in range(columns):
if column >= row:
utm[row][column] = int(input("upper_triangular_matrix[%d][%d]: "
% (row, column)))
except ValueError as e:
print("errcode: %s" % str(1001))
print("errmsg: %s" % str(e))
exit(1001)
except MatrixException as e:
print("errcode: %s" % e.code)
print("errmsg: %s" % e.message)
exit(e.code)
# 2. 壓縮右上三角矩陣
try:
array_size = ((1 + rows) * rows) // 2
compress = [None] * array_size
pos = 0
for row in range(rows):
for column in range(columns):
if column >= row:
compress[pos] = utm[row][column]
pos += 1
if None in compress:
print("compress: %s" % compress)
raise MatrixException("Compress upper triangular matrix failed.", 1002)
except MatrixException as e:
print("errcode: %s" % e.code)
print("errmsg: %s" % e.message)
exit(e.code)
# 3. 打印結果
print("------upper triangular matrix------")
for row in range(rows):
message = "|\t"
for column in range(columns):
message += str(utm[row][column]) + "\t"
message += "|"
print(message)
print("------compress upper triangular matrix --> list ------")
print(compress)
4. 代碼走讀
"""
Copyright TCatTime
"""
# 自定義壓縮異常
class MatrixException(Exception):
def __init__(self, message, code):
self.message = message
self.code = code
# 1. 輸入一個右上三角矩陣
try:
# 輸入右上三角矩陣的行數,行數不大於0時報錯
rows = int(input("Input matrix rows: "))
if rows <= 0:
raise MatrixException("Matrix rows can not less than zero.", 1002)
# 列數與行數保持相等
columns = rows
# 輸入默認值(通常爲0)
default_value = int(input("Input default value: "))
# 使用默認值初始化右上三角矩陣,並提示用戶填充
utm = [[default_value] * columns for row in range(rows)]
for row in range(rows):
for column in range(columns):
if column >= row:
utm[row][column] = int(input("upper_triangular_matrix[%d][%d]: "
% (row, column)))
# 當用戶輸入的數據不是一個整數時,會報錯並退出
except ValueError as e:
print("errcode: %s" % str(1001))
print("errmsg: %s" % str(e))
exit(1001)
except MatrixException as e:
print("errcode: %s" % e.code)
print("errmsg: %s" % e.message)
exit(e.code)
# 2. 壓縮右上三角矩陣
try:
# 初始化壓縮列表,並使用None填充
array_size = ((1 + rows) * rows) // 2
compress = [None] * array_size
# 將右上三角矩陣的數據寫入壓縮l
pos = 0
for row in range(rows):
for column in range(columns):
if column >= row:
compress[pos] = utm[row][column]
pos += 1
if None in compress:
print("compress: %s" % compress)
raise MatrixException("Compress upper triangular matrix failed.", 1002)
except MatrixException as e:
print("errcode: %s" % e.code)
print("errmsg: %s" % e.message)
exit(e.code)
# 3. 打印結果
print("------upper triangular matrix------")
for row in range(rows):
message = "|\t"
for column in range(columns):
message += str(utm[row][column]) + "\t"
message += "|"
print(message)
print("------compress upper triangular matrix --> list ------")
print(compress)
傳送門
測試用例
1、將如下的右上三角矩陣壓縮
5 | 6 | 7 |
0 | 3 | 9 |
0 | 0 | 1 |
Input matrix rows: 3
Input default value: 0
upper_triangular_matrix[0][0]: 5
upper_triangular_matrix[0][1]: 6
upper_triangular_matrix[0][2]: 7
upper_triangular_matrix[1][1]: 3
upper_triangular_matrix[1][2]: 9
upper_triangular_matrix[2][2]: 1
------upper triangular matrix------
| 5 6 7 |
| 0 3 9 |
| 0 0 1 |
------compress upper triangular matrix --> list ------
[5, 6, 7, 3, 9, 1]
2、輸入的行數數據測試
1、輸入0
Input matrix rows: 0
errcode: 1002
errmsg: Matrix rows can not less than zero.
2、輸入負數
Input matrix rows: -4
errcode: 1002
errmsg: Matrix rows can not less than zero.
3、輸入1
Input matrix rows: 1
Input default value: 0
upper_triangular_matrix[0][0]: 6
------upper triangular matrix------
| 6 |
------compress upper triangular matrix --> list ------
[6]
4、輸入浮點數
Input matrix rows: 4.8
errcode: 1001
errmsg: invalid literal for int() with base 10: '4.8'
5、輸入字符
Input matrix rows: s
errcode: 1001
errmsg: invalid literal for int() with base 10: 's'
3、輸入的默認值測試
1、壓縮如下矩陣。
5 | 6 | 7 |
13 | 3 | 9 |
13 | 13 | 1 |
將默認值default設置爲13.
Input matrix rows: 3
Input default value: 13
upper_triangular_matrix[0][0]: 5
upper_triangular_matrix[0][1]: 6
upper_triangular_matrix[0][2]: 7
upper_triangular_matrix[1][1]: 3
upper_triangular_matrix[1][2]: 9
upper_triangular_matrix[2][2]: 1
------upper triangular matrix------
| 5 6 7 |
| 13 3 9 |
| 13 13 1 |
------compress upper triangular matrix --> list ------
[5, 6, 7, 3, 9, 1]
2、輸入的默認值爲浮點數
Input matrix rows: 3
Input default value: 3.6
errcode: 1001
errmsg: invalid literal for int() with base 10: '3.6'
3、輸入的默認值爲字符:
Input matrix rows: 3
Input default value: d
errcode: 1001
errmsg: invalid literal for int() with base 10: 'd'
4、輸入的矩陣值測試
1、正確的測試值在上例已有演示。
2、矩陣值輸入的是字符:
Input matrix rows: 3
Input default value: 0
upper_triangular_matrix[0][0]: a
errcode: 1001
errmsg: invalid literal for int() with base 10: 'a'
3、矩陣值輸入的是浮點數:
Input matrix rows: 3
Input default value: 0
upper_triangular_matrix[0][0]: 1.3
errcode: 1001
errmsg: invalid literal for int() with base 10: '1.3'