⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 sparsem_anslysis.cpp

📁 是稀疏矩阵库以及全矩阵和稀疏矩阵分析程序源代码
💻 CPP
字号:



#include"stdafx.h"
#include"Analysis.h"
#include"Sparsem.h"
#include ".\analysis.h"
CSparseMatrix znmna_list; //声明一个稀疏矩阵类对象
void Analysis::GetVBrNum()
{
	int i,j,k,t,tt;
	bNUM_vbNUM=new int[BranchNumber+1];
	vBranchNumber=0;
	for(i=1;i<BranchNumber+1;i++) bNUM_vbNUM[i]=0;//初始化
	for(i=1;i<BranchNumber+1;i++)
	{
		t=Branch[i].type;
		if(t==VS||t==VCVS||t==OPAMP)//必然的电压定义之路
		{
			vBranchNumber++;
			bNUM_vbNUM[i]=vBranchNumber;
		}
		else if(t==CCVS)
		{
			vBranchNumber++;//本身为电压定义支路
			bNUM_vbNUM[i]=vBranchNumber;
			k=Branch[i].ncfrom;
			tt=Branch[k].type;
			if((tt==G||tt==R)&&Branch[k].ncfrom==0&&Branch[k].ncto==0)
			{
				vBranchNumber++;//控制之路也为电压定义支路
				bNUM_vbNUM[k]=vBranchNumber;
				Branch[k].ncto=1;//做一个标记
			}
		}
		else if(t==CCCS){
			k=Branch[i].ncfrom;
			tt=Branch[k].type;
			if((tt==G||tt==R)&&Branch[k].ncfrom==0&&Branch[k].ncto==0)
			{
				vBranchNumber++;//控制之路作为电压定义支路
				bNUM_vbNUM[k]=vBranchNumber;
				Branch[k].ncto=1;
			}
		}
		else if((t==G||t==R)&&Branch[i].ncfrom==1)
		{	//指定为电压定义支路
			vBranchNumber++;
			bNUM_vbNUM[i]=vBranchNumber;
		}
	}
	vbNUM_bNUM=new int[vBranchNumber+1];
	for (i=1;i<BranchNumber+1;i++)//电压定义支路到支路的映射
	{
		j=bNUM_vbNUM[i];
		vbNUM_bNUM[j]=i;
	}

}
/********************************************************/ 

void Analysis::Fromlist_symlu()
{

	znmna_list.newList(RANK,NONZERO,1);//秩为100,稀疏度为0.3 ,全主元排序
	znmna_list.setRankList(NodeNumber+vBranchNumber);//置list的阶数
	int k,kk,nb,t,nf,nt,ncf,nct;
	nb=NodeNumber+vBranchNumber+1;
	for(int i=1;i<BranchNumber+1;i++)
	{
		br=Branch+i;
		t=br->type;
		nf=br->nfrom;
		nt=br->nto;
		ncf=br->ncfrom;
		nct=br->ncto;
		if(t==R)
		{
			if(ncf==0&&nct==0)//非电压定义支路
			{
				if(nf==0) znmna_list.insertListEle(nt,nt);
				else if(nt==0)znmna_list.insertListEle(nf,nf);
				else{
					znmna_list.insertListEle(nf,nf);
					znmna_list.insertListEle(nt,nt);
					znmna_list.insertListEle(nf,nt);
					znmna_list.insertListEle(nt,nf);//对Y的贡献
			 }
			}
			else
			{
				k=br->number;
				k=bNUM_vbNUM[k];
				k=k+NodeNumber;
				znmna_list.insertListEle(nf,k);//
				znmna_list.insertListEle(nt,k);//对B的贡献,即对节电电流的贡献
				znmna_list.insertListEle(k,nf);/////对C的贡献
				znmna_list.insertListEle(k,nt);/////           为支路特性
				znmna_list.insertListEle(k,k);//////对D的贡献
			}
		}
		else if(t==G)
		{
			if(ncf==0&&nct==0)
			{
				if(nf==0) znmna_list.insertListEle(nt,nt);
				else if(nt==0) znmna_list.insertListEle(nf,nf);
				else{
					znmna_list.insertListEle(nf,nf);
					znmna_list.insertListEle(nt,nt);
					znmna_list.insertListEle(nt,nf);///////对Y的贡献
					znmna_list.insertListEle(nf,nt);
				}
			}
			else{
				k=br->number;
				k=bNUM_vbNUM[k];
				k=k+NodeNumber;
				znmna_list.insertListEle(nf,k);//
				znmna_list.insertListEle(nt,k);//对B的贡献
				znmna_list.insertListEle(k,nf);///对C的贡献
				znmna_list.insertListEle(k,nt);///
				znmna_list.insertListEle(k,k);//////对D的贡献
			}
		}
		else if(t==VCCS)  //电压控制电流源支路
		{
			znmna_list.insertListEle(nf,ncf);// 修正,书上有误                                                                                                                                                                                                                                                                                                    
			znmna_list.insertListEle(nf,nct);
			znmna_list.insertListEle(nt,ncf);
			znmna_list.insertListEle(nt,nct);
		}
		else if(t==CCCS)	//电流控制电流源支路
		{
			k=ncf;
			k=bNUM_vbNUM[k];
			k=k+NodeNumber;
			znmna_list.insertListEle(nf,k);
			znmna_list.insertListEle(nt,k);
		}
		else if(t==VCVS)
		{
			k=br->number;
			k=bNUM_vbNUM[k];
			k=k+NodeNumber;
			znmna_list.insertListEle(nf,k);
			znmna_list.insertListEle(nt,k);
			znmna_list.insertListEle(k,nf);
			znmna_list.insertListEle(k,nt);
			znmna_list.insertListEle(k,ncf);
			znmna_list.insertListEle(k,nct);
		}
		else if(t==CCVS)
		{
			kk=ncf;	//修正
			kk=bNUM_vbNUM[kk];
			kk+=NodeNumber;
			k=br->number;
			k=bNUM_vbNUM[k];
			k+=NodeNumber;
			znmna_list.insertListEle(nf,k);
			znmna_list.insertListEle(nt,k);
			znmna_list.insertListEle(k,nf);
			znmna_list.insertListEle(k,nt);
			znmna_list.insertListEle(k,kk);
		}
		else if(t==OPAMP)
		{
			k=br->number;
			k=bNUM_vbNUM[k];
			k=k+NodeNumber;
			znmna_list.insertListEle(nf,k);
			znmna_list.insertListEle(nt,k);
			znmna_list.insertListEle(k,ncf);
			znmna_list.insertListEle(k,nct);
		}
		else if(t==VS)
		{
			k=br->number;
			k=bNUM_vbNUM[k];
			k=k+NodeNumber;
			znmna_list.insertListEle(nf,k);
			znmna_list.insertListEle(nt,k);
			znmna_list.insertListEle(k,nf);
			znmna_list.insertListEle(k,nt);
		}
	}
	znmna_list.covListTab();

	//先优化排序,在转化成三角形表,因为双链表是动态结构
	//方便生成,插入,删除,和优化排序,
	//然后再转化成三角形表进行LU分解
}

void Analysis::InsertB_symFE()//插入右端向量,并进行符号前消
{
	for(int i=1;i<BranchNumber+1;i++)
	{
		BRANCH*	br=Branch+i;
		int t=br->type;
		int nf=br->nfrom;
		int nt=br->nto;
		if(t==CS)
		{	
			if(nf==0)znmna_list.insertB(nt);
			else if(nt==0)znmna_list.insertB(nf);
			else {
				znmna_list.insertB(nf);
				znmna_list.insertB(nt);
			}
		}
		else if (t==VS){
			int k=br->number;
			k=bNUM_vbNUM[k];
			k=k+NodeNumber;
			znmna_list.insertB(k);
		}
	}
	znmna_list.symFE();//先有端向量填元处理,再符号前消

}

void Analysis:: LoadAData_numLU()//装配数值,进行数值分解
{
	int k,kk;
	for(int i=1;i<BranchNumber+1;i++)
	{
		BRANCH* br=Branch+i;
		char t=br->type;
		int nf=br->nfrom;
		int nt=br->nto;
		int ncf=br->ncfrom;
		int nct=br->ncto;
		double val=br->value;

		if(t==R)//电阻支路
		{
			if(ncf==0&&nct==0)//非电压定义支路
			{
				val=1.0/val;//转换成电导
				if(nf==0)znmna_list.insertCoef(nt,nt,val);//始节点为0
				else if(nt==0)znmna_list.insertCoef(nf,nf,val);//终节点为零
				else
				{
					znmna_list.insertCoef(nf,nf,val); 
					znmna_list.insertCoef(nt,nt,val);
					znmna_list.insertCoef(nf,nt,-val);
					znmna_list.insertCoef(nt,nf,-val);
					//对Y的导纳贡献,通过节点-节点关系来写
					//其实此时看做电导,形势是一样的·	
				}
			}
			else
			{      //电压定义电阻支路
				k=br->number;
				k=bNUM_vbNUM[k];//电压定义支路号
				k=k+NodeNumber;

				znmna_list.insertCoef(nf,k,1);//修正 书上为val,对B贡献,即对该节点节点电流贡献
				znmna_list.insertCoef(nt,k,-1);//修正 
				znmna_list.insertCoef(k,nf,1.0); //	 
				znmna_list.insertCoef(k,nt,-1.0);//这3项为支路特性 Unf-Unto-val*jk=0
				znmna_list.insertCoef(k,k,-1.0*val);
				
			}
		}
		else if(t==G)//电导支路
		{
			if(ncf==0&&nct==0)//非电压定义支路
			{
				if(nf==0)znmna_list.insertCoef(nt,nt,val);
				else if(nt==0)znmna_list.insertCoef(nf,nf,val);
				else
				{
					znmna_list.insertCoef(nf,nf,val);
					znmna_list.insertCoef(nt,nt,val);
					znmna_list.insertCoef(nf,nt,-1.0*val);
					znmna_list.insertCoef(nt,nf,-1.0*val);
					
				}
			}
			else//电压定义电导支路
			{
				k=br->number;
				k=bNUM_vbNUM[k];//电压定义支路号
				k=k+NodeNumber;
				znmna_list.insertCoef(nf,k,1.0);
				znmna_list.insertCoef(nt,k,-1.0);  //导纳贡献
				znmna_list.insertCoef(k,nf,1.0);  //对C贡献
				znmna_list.insertCoef(k,nt,-1.0);
				znmna_list.insertCoef(k,k,-1.0/val); //对D贡献,注意此时支路特性为Unf-Unto-jk/G=0

			}
		}
		else if(t==VCCS)//电压控制电流源支路
		{
			znmna_list.insertCoef(nf,ncf,val);	//对节点nf的电流贡献用g(Uncf-Uncto)	表示
			znmna_list.insertCoef(nf,nct,-1*val); 
			znmna_list.insertCoef(nt,ncf,-1*val);//对nto贡献,左边为流出节点的电流
			znmna_list.insertCoef(nt,nct,val);
			
		}
		else if(t==CCCS)//电流控制电流源支路
		{
			k=ncf;
			k=bNUM_vbNUM[k];//控制支路号
			k=k+NodeNumber;//电压定义支路号
			znmna_list.insertCoef(nf,k,val); ///对B的贡献,流出nf的电流a*jk
			znmna_list.insertCoef(nt,k,-1.0*val); //流出nto的电流为-a*jk

		}
		else if(t==VCVS)//电压控制电压源支路
		{
			k=br->number;//支路号
			k=bNUM_vbNUM[k];//电压定义支路号
			k=k+NodeNumber;
			znmna_list.insertCoef(nf,k,1.0); //
			znmna_list.insertCoef(nt,k,-1.0);// 对B的贡献,即电压定义支路对节点的电流贡献
			znmna_list.insertCoef(k,nf,1.0);  
			znmna_list.insertCoef(k,nt,-1.0);  
			znmna_list.insertCoef(k,ncf,-1.0*val); 
			znmna_list.insertCoef(k,nct,val);// 以上四个为支路特性,即Unf-Unto-(Uncf-Uncto)=0

		}
		else if(t==CCVS)//电流控制电压源支路
		{
			kk=ncf;//控制支路号
			kk=bNUM_vbNUM[kk];
			kk=kk+NodeNumber;
			k=br->number;//支路号
			k=bNUM_vbNUM[k];
			k=k+NodeNumber;
			znmna_list.insertCoef(nf,k,1.0);//对节点电流的贡献
			znmna_list.insertCoef(nt,k,-1.0);//
			znmna_list.insertCoef(k,nf,1.0);// 支路特性Unf_Unto-rm*jk=0
			znmna_list.insertCoef(k,nt,-1.0);//对C的贡献
			znmna_list.insertCoef(k,kk,-1.0*val);//对D的贡献

		}
		else if(t==OPAMP)//理想运算放大器,因为虚断,没有电流贡献多一看作一条电压定义支路
		{
			k=br->number;//支路号
			k=bNUM_vbNUM[k];//电压定义支路号
			k=k+NodeNumber;

			znmna_list.insertCoef(nf,k,1.0);//
			znmna_list.insertCoef(nt,k,-1.0);//对Y的贡献,
			znmna_list.insertCoef(k,ncf,1.0);//	输入口支路特性即虚短,Ui-Uj=0;
			znmna_list.insertCoef(k,nct,-1.0);

		}
		else if(t==VS)//独立电压源
		{
			k=br->number;//支路号
			k=bNUM_vbNUM[k];//电压定义支路号
			k=k+NodeNumber;
			znmna_list.insertCoef(nf,k,1.0);  //对节点电流的贡献即Y
			znmna_list.insertCoef(nt,k,-1.0); //
			znmna_list.insertCoef(k,nf,1.0);   //Unf-Unto=0
			znmna_list.insertCoef(k,nt,-1.0); // 支路特性,C
		}
	}
	znmna_list.numLU();			  
}
void Analysis:: LoadBData_BS()

{
	int i,t,nf,nt,ncf,nct,k;
	double val;//装配右端向量数值
	for(i=1;i<BranchNumber+1;i++)
	{
		BRANCH*br=Branch+i;
		t=br->type;
		nf=br->nfrom;
		nt=br->nto;
		ncf=br->ncfrom;
		nct=br->ncto;
		val=br->value;

		if(t==CS)
		{
			znmna_list.insertBVal( nf,-1*val);//修正
			znmna_list.insertBVal(nt,val);///因为右边是流入节点的独立电流源的和
			//而我们规定电流源的方向为nf->nto

		}		
		else if(t==VS)	
		{
			k=br->number;
			k=bNUM_vbNUM[k];
			k=k+NodeNumber;
			znmna_list.insertBVal(k,val);  //第k条电压定义支路
		}

	}

	znmna_list. makeSolution();// 数值前消、后代,获得Tab中的解
	CString Total;	
	CString outmsg;
	double m_out;
	for( i=1;i<NodeNumber+vBranchNumber+1;i++)
	{

		m_out=znmna_list.getX(i);
		if(i<NodeNumber+1)
			outmsg.Format("u[%d]=%4.4f\n",i,m_out);  
		else  {
			int v=vbNUM_bNUM[i-NodeNumber];
			outmsg.Format("vBranchNumber=%d; I[%d]=%4.8f\n",v,i-NodeNumber, (double) m_out);
		}
		Total=Total+outmsg;

	}
	AfxMessageBox(Total,MB_OK|MB_ICONINFORMATION);
	znmna_list.deleteList();
	znmna_list.delete_tableT();

}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -