好久没有写过C#了。不过C#确实非常方便,代码写起来也很顺。这个代码是描述行逻辑链接的三元组顺序表。(处理稀疏矩阵效率要比经典算法高得多的~而且也更节省存储空间。)
//#defineOUTPUT_DEBUG
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
namespace MatrixCSharp
{
public class Matrix {
public struct PolyEx {
publicint i;
publicint j;
publicint val;
}
publicMatrix() {
polyExList = new List<PolyEx>();
row = col = tu = 0;
}
publicMatrix(int[,] array)
:this(){
LoadPolyExList(array);
}
public void LoadPolyExList(int[,]array) {
polyExList.Clear();
row = array.GetLength(0);
col = array.GetLength(1);
tu = 0;
for(int i = 0; i < row; ++i)
{
for(int j = 0; j < col; ++j)
{
if(array[i, j] != 0)
{
PolyEx pe = new PolyEx();
pe.i = i;
pe.j = j;
pe.val = array[i, j];
polyExList.Add(pe);
++tu;
}
}
}
firstIndexs = GetFirstIndex(1);
}
//
// 1 =>row
// 0 =>col
//
privateint[] GetFirstIndex(intrOrC) {
// Readall the column numbers.
intsize = 0;
if(rOrC == 1){
size = row;
}
else{
size = col;
}
int[]num4Col = new int[size];
int[]indexs = new int[size];
foreach(PolyEx pe inpolyExList) {
if(rOrC == 1){
num4Col[pe.i]++;
}
else{
num4Col[pe.j]++;
}
}
for(int i = 0; i < size; ++i){
if(i > 0)
{
indexs[i] += num4Col[i - 1]+ indexs[i - 1];
}
else
{
indexs[i] = 0;
}
}
#if OUTPUT_DEBUG
Console.WriteLine("FirstIndexs:");
foreach (int i in indexs) {
Console.Write(i + "");
}
Console.WriteLine();
#endif
returnindexs;
}
public void Translate() {
PolyEx[] resList = new PolyEx[tu];
int[]colFirstIndexs = GetFirstIndex(0);
intindex = -1;
foreach(PolyEx pe inpolyExList) {
PolyExpeNew = new PolyEx();
peNew.j = pe.i;
peNew.i = pe.j;
peNew.val = pe.val;
index = colFirstIndexs[pe.j];
resList[index] = peNew;
colFirstIndexs[pe.j]++;
}
polyExList = new List<PolyEx>(resList);
firstIndexs = colFirstIndexs;
inttemp = row;
row = col;
col = row;
}
public Matrix Mul(Matrixm2) {
if(this.col != m2.row) {
returnnull;
}
MatrixmRes = new Matrix();
// 累加器
int[] acc = new int[m2.col];
for(int i = 0; i < polyExList.Count; ++i) {
if(i > 0) {
if(polyExList[i].i != polyExList[i - 1].i) {
for (int j = 0; j < m2.col;++j)
{
if (acc[j] != 0)
{
PolyEx pe = new PolyEx();
pe.i =polyExList[i].i;
pe.j = j;
pe.val =acc[j];
Console.WriteLine("Col:"+ j + " Val:" + pe.val);
mRes.polyExList.Add(pe);
}
}
setZero(acc);
}
}
intcolIndex = m2.firstIndexs[polyExList[i].j];
while(colIndex < m2.polyExList.Count
&&m2.polyExList[colIndex].i == polyExList[i].j) {
#if OUTPUT_DEBUG
Console.WriteLine("i=> " + polyExList[i].i);
Console.WriteLine("m2j => " + m2.polyExList[colIndex].j);
Console.WriteLine();
#endif
acc[m2.polyExList[colIndex].j]
+=m2.polyExList[colIndex].val * polyExList[i].val;
colIndex++;
}
}
for(int j = 0; j < m2.col; ++j)
{
if(acc[j] != 0)
{
PolyExpe = new PolyEx();
pe.i =polyExList[polyExList.Count - 1].i;
pe.j = j;
pe.val = acc[j];
#if OUTPUT_DEBUG
Console.WriteLine("Col:" + j + " Val:" + pe.val);
#endif
mRes.polyExList.Add(pe);
}
}
mRes.row = row;
mRes.col = m2.col;
mRes.firstIndexs = mRes.GetFirstIndex(1);
mRes.tu = mRes.polyExList.Count;
returnmRes;
}
privatevoid setZero(int[]array) {
for(int i = 0; i < array.Length; ++i) {
array[i] = 0;
}
}
public int Row {
get{ return row; }
}
public int Col {
get{ return col; }
}
public override stringToString()
{
StringBuildersb = new StringBuilder();
sb.AppendLine("i\tj\tvalue");
sb.AppendLine("--\t--\t-----");
foreach(PolyEx pe inpolyExList) {
sb.AppendFormat("{0}\t{1}\t{2}\n",
pe.i,
pe.j,
pe.val);
}
returnsb.ToString();
}
privateList<PolyEx>polyExList;
privateint[] firstIndexs; // 记录每一行非零元的起始位置
privateint row;
privateint col;
privateint tu;
}
class Program
{
static int[,] SimpleMul(int[,]m1, int[,] m2) {
introw1 = m1.GetLength(0);
intcol1 = m1.GetLength(1);
introw2 = m2.GetLength(0);
intcol2 = m2.GetLength(1);
int[,]mRes = new int[row1,col2];
for(int i = 0; i < row1; ++i) {
for(int j = 0; j < col2; ++j) {
mRes[i, j] = 0;
for(int k = 0; k < col1; ++k) {
mRes[i,j] += m1[i,k] *m2[k,j];
}
}
}
for(int i = 0; i < row1; ++i) {
for(int j = 0; j < col2; ++j) {
if(mRes[i, j] == 0){
Console.Write("-\t");
}
else{
Console.Write(mRes[i, j] + "\t");
}
}
Console.WriteLine();
}
returnmRes;
}
static void Main(string[]args)
{
int[,]test = {
{ 0, 0, 1, 0, 0, 0, 1, 0, 3,4},
{ 3, 0, 0, 0, 0, 0, 7, 0, 3,4},
{ 0, 4, 9, 0, 0, 5, 1, 0, 3,4},
{ 0, 0, 0, 13, 0, 0, 8, 0, 3, 4},
{ 0, 0, 0, 0, 0, 0, 9, 0, 3,4},
{ 0, 0, 0, 0, 0, 0, 1, 0, 3,4},
};
int[,]test2 = {
{ 1, 0, 8, 0, 0, 1},
{ 0, 0, 0, 0, 3, 0},
{ 0, 3, 0, 0, 0, 0},
{ 0, 5, 0, 0, 0, 0},
{ 0, 5, 0, 0, 0, 0},
{ 0, 5, 4, 0, 0, 0},
{ 0, 9, 0, 0, 1, 0},
{ 0, 5, 0, 0, 0, 0},
{ 0, 5, 0, 5, 0, 0},
{ 0, 5, 0, 0, 0, 0},
};
Matrixm = new Matrix(test);
Matrixm2 = new Matrix(test2);
Console.WriteLine(m);
Console.WriteLine(m2);
Matrixres = m.Mul(m2);
Console.WriteLine(res);
SimpleMul(test, test2);
//m.Translate();
//Console.WriteLine(m);
Console.ReadKey();
}
}
}