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

📄 calculate2.c

📁 这是一个采用快速傅立叶算法计算电能量的例程
💻 C
📖 第 1 页 / 共 2 页
字号:
	      fCalQ[1]= (fValX1 * fTmpR1 - fValR1 * fTmpX1);				//记录各个通道的计算功率:浮点数类型
      
       }
       else{
	      fCalP[1]= 0;
	      fCalQ[1]= 0;													//两表法不计算B相电压、电流
       }

       calculate();   //供显示和通信用,也是每20ms计算一次
	   AlertHandle(); //参数越限报警的处理
	   //以下开始电度量的计算
	}				//END OF bInt20ms==TRUE
}        


//供显示和通信用的计算函数
extern bit permit_freq;
void calculate(void)
{
   unsigned char i,j;
   static xdata unsigned char CalCount=0;
   xdata float fCalUI[6];						//相电压、电流有效值。按照以下顺序排列:Ua、Ia、Ub、Ib、Uc、Ic
   xdata float fCalUU[3];						//线电压有效值
   static xdata float VectorUUR[3]={0,0,0};		//计算线电压矢量的实部
   static xdata float VectorUUX[3]={0,0,0};		//计算线电压矢量的虚部
   static xdata float TmpCalUI[6]={0,0,0,0,0,0};//相电压、电流有效值的累积。按照以下顺序排列:Ua、Ia、Ub、Ib、Uc、Ic
   static xdata float TmpCalP[4]={0,0,0,0};		//有功功率的累积值
   static xdata float TmpCalQ[4]={0,0,0,0};		//无功功率的累积值
   static xdata float TmpCalS[4]={0,0,0,0};
   static xdata float TmpCalUU[3]={0,0,0};		//线电压有效值的累积
//   static xdata float TmpFrequence=0;             //频率的累积
   
   //=========================================================================================
   //									Part 1 :  电压、电流的计算处理
   //=========================================================================================
   if(bMeter3!=0){		//装置采用三表法接线
        VectorUUR[0]=VectorR[0]-VectorR[2];		//Uab.R=Ua.R-Ub.R
        VectorUUR[1]=VectorR[2]-VectorR[4];		//Ubc.R=Ub.R-Uc.R
        VectorUUR[2]=VectorR[4]-VectorR[0];		//Uca.R=Uc.R-Ua.R
        VectorUUX[0]=VectorX[0]-VectorX[2];		//Uab.X=Ua.X-Ub.X
        VectorUUX[1]=VectorX[2]-VectorX[4];		//Ubc.X=Ub.X-Uc.X
        VectorUUX[2]=VectorX[4]-VectorX[0];		//Uca.X=Uc.X-Ua.X
   
        for(i=0;i<3;i++){
          fCalUU[i] = sqrt(VectorUUR[i]*VectorUUR[i]+VectorUUX[i]*VectorUUX[i]);
          if(fCalUU[i]<fCalUSet) fCalUU[i]=0;
        }
        for(i=0;i<3;i++){					
          j=i*2; 
          fCalUI[j]=sqrt(VectorR[j]*VectorR[j]+VectorX[j]*VectorX[j]);
          if(fCalUI[j]<fCalUSet){ 					//计算相电压的幅值
            fCalUI[j]=0;
            fCalP[i]=0;
            fCalQ[i]=0;
          }  
          j=i*2+1; 
          fCalUI[j]=sqrt(VectorR[j]*VectorR[j]+VectorX[j]*VectorX[j]);
          if(fCalUI[j]<fCalISet){ 					//计算相电流的幅值
            fCalUI[j]=0;
            fCalP[i]=0;
            fCalQ[i]=0;
          }  
        }
        fCalP[3] = fCalP[0] + fCalP[1] + fCalP[2];
        fCalQ[3] = fCalQ[0] + fCalQ[1] + fCalQ[2];
   }
   else {		//装置采用两表法接线.
        for(i=0;i<2;i++){								//两表法不计算B相,设其为0					
          j=i*4; 
          fCalUI[j]=sqrt(VectorR[j]*VectorR[j]+VectorX[j]*VectorX[j]);
          if(fCalUI[j]<fCalUSet){ 					//计算相电压的幅值
            fCalUI[j]=0;
            fCalP[i*2]=0;
            fCalQ[i*2]=0;
          }  
          j=i*4+1; 
          fCalUI[j]=sqrt(VectorR[j]*VectorR[j]+VectorX[j]*VectorX[j]);
          if(fCalUI[j]<fCalISet){ 					//计算相电流的幅值
            fCalUI[j]=0;
            fCalP[i*2]=0;
            fCalQ[i*2]=0;
          }  
        }
        fCalUI[2]=fCalUI[3]=fCalP[1]=fCalQ[1]=0;

        for(i=0;i<3;i++) fCalUU[i] = fCalUI[i*2];		//两表法时线电压等于相电压
        
        fCalP[3] = fCalP[0] + fCalP[2];
        fCalQ[3] = fCalQ[0] + fCalQ[2];
   } 		//装置采用三表法/两表法处理结束

   fCalS[0]=sqrt(fCalP[0]*fCalP[0] + fCalQ[0]*fCalQ[0]);
   fCalS[1]=sqrt(fCalP[1]*fCalP[1] + fCalQ[1]*fCalQ[1]);
   fCalS[2]=sqrt(fCalP[2]*fCalP[2] + fCalQ[2]*fCalQ[2]);
   fCalS[3]=sqrt(fCalP[3]*fCalP[3] + fCalQ[3]*fCalQ[3]); //每一周波计算一次视在功率
   
   //=========================================================================================
   //									Part 2 :  电度计算
   //=========================================================================================
        if(fCalP[3]>0) {				//正向有功电度
         fCalValWh0 += fCalP[3];			//累积有功电度
         //每20ms进行一次计算,对于1kVA的功率相当于20ms/(60*60*1000)ms度,即对于1kVA的电量数据,计数满18000时为1度。
         if(fCalValWh0 > KVA_num) {		//每0.1度电记录一次结果到NVRAM中
            i=(int)(fCalValWh0/KVA_num);
            fCalValWh0 -= i*KVA_num;
            if(fCalValWh0>KVA_num||fCalValWh0<0)     //防止飞转,刘兵加
               fCalValWh0=0;
			else{
               Ram_PK0_Init += i;
               if(Ram_PK0_Init>9999) {		//超过999.9度将计算结果显示为MW
          	      Ram_PG0_Init++;
          	      Ram_PK0_Init -= 9999;
				  if(Ram_PK0_Init>9999)             //防止出现怪号
				  Ram_PK0_Init=0;
               }
			}
         }  
       }
       else {						//负向有功电度
		 fCalValWh1 -= fCalP[3];			//累积有功电度
         //每20ms进行一次计算,对于1kVA的功率相当于20ms/(60*60*1000)ms度,即对于1kVA的电量数据,计数满18000时为1度。
         if(fCalValWh1 > KVA_num) {		//每0.1度电记录一次结果到NVRAM中
            i=(int)(fCalValWh1/KVA_num);
            fCalValWh1 -= i*KVA_num;
            if(fCalValWh1>KVA_num||fCalValWh1<0)     //防止飞转,刘兵加
               fCalValWh1=0;
			else{
               Ram_PK1_Init +=i;
               if(Ram_PK1_Init>9999) {			//超过999.9度将计算结果显示为MW
          	      Ram_PG1_Init++;
          	      Ram_PK1_Init -= 9999;
				  if(Ram_PK1_Init>9999)         //防止怪号
				  Ram_PK1_Init=0;
               }
			}
         }  
       }  		  

       if(fCalQ[3]>0) {				//正向无功电度
         fCalValvar0 += fCalQ[3];			//累积无功电度
         //每20ms进行一次计算,对于1kVA的功率相当于20ms/(60*60*1000)ms度,即对于1kVA的电量数据,计数满18000时为1度。
         if(fCalValvar0 > KVA_num) {		//每0.1度电记录一次结果到NVRAM中
            i=(int)(fCalValvar0/KVA_num);
            fCalValvar0 -= i*KVA_num;
			if(fCalValvar0>KVA_num||fCalValvar0<0)    //防止出现飞转
			   fCalValvar0=0;
			else{
               Ram_QK0_Init +=i;
               if(Ram_QK0_Init>9999) {		//超过999.9度将计算结果显示为MVAR
          	      Ram_QG0_Init++;
          	      Ram_QK0_Init -=9999;
				  if(Ram_QK0_Init>9999)     //防止出现怪号
				  Ram_QK0_Init=0;          
               }
			}
         }  
       }
       else {						//负向无功电度
		 fCalValvar1 -= fCalQ[3];			//累积无功电度
         //每20ms进行一次计算,对于1kVA的功率相当于20ms/(60*60*1000)ms度,即对于1kVA的电量数据,计数满18000时为1度。
         if(fCalValvar1 > KVA_num) {		//每0.1度电记录一次结果到NVRAM中
            i=(int)(fCalValvar1/KVA_num);
            fCalValvar1 -= i*KVA_num;
			if(fCalValvar1>KVA_num||fCalValvar1<0)      //防止出现飞转
			fCalValvar1=0;
			else{
               Ram_QK1_Init +=i;
               if(Ram_QK1_Init>9999) {		//超过999.9度将计算结果显示为MVAR
          	      Ram_QG1_Init++;
          	      Ram_QK1_Init -=9999;    
				  if(Ram_QK1_Init>9999)     //防止出现怪号  
				  Ram_QK1_Init=0;
               }
			}
         }  
       }  
	   //视在电度
         fCalValVA += fCalS[3];			//累积有功电度
         //每20ms进行一次计算,对于1kVA的功率相当于20ms/(60*60*1000)ms度,即对于1kVA的电量数据,计数满18000时为1度。
         if(fCalValVA > KVA_num) {		//每0.1度电记录一次结果到NVRAM中
            i=(int)(fCalValVA/KVA_num);
            fCalValVA -= i*KVA_num;
            if(fCalValVA>KVA_num||fCalValVA<0)     //防止飞转,刘兵加
               fCalValVA=0;
			else{
               Ram_SK_Init += i;
               if(Ram_SK_Init>9999) {		//超过999.9度将计算结果显示为MVA
          	      Ram_SG_Init++;
          	      Ram_SK_Init -= 9999;
				  if(Ram_SK_Init>9999)             //防止出现怪号
				  Ram_SK_Init=0;
               }
			}
         }  

	   //电度总量的计算:1.计算有功电度总量
	   if(Ram_PK0_Init+Ram_PK1_Init>9999){
          PE_total_l.IntData=Ram_PK0_Init+Ram_PK1_Init-9999;
		  PE_total_h.IntData=Ram_PG0_Init+Ram_PG1_Init+1;
	   }
	   else{
          PE_total_l.IntData=Ram_PK0_Init+Ram_PK1_Init;
		  PE_total_h.IntData=Ram_PG0_Init+Ram_PG1_Init;
	   }
	   //电度总量的计算:1.计算无功电度总量
	   if(Ram_QK0_Init+Ram_QK1_Init>9999){
          QE_total_l.IntData=Ram_QK0_Init+Ram_QK1_Init-9999;
		  QE_total_h.IntData=Ram_QG0_Init+Ram_QG1_Init+1;
	   }
	   else{
          QE_total_l.IntData=Ram_QK0_Init+Ram_QK1_Init;
		  QE_total_h.IntData=Ram_QG0_Init+Ram_QG1_Init;
	   }
       //电度净值的计算:1.计算有功电度净值
       if(Ram_PK0_Init>=Ram_PK1_Init){                  
          if(Ram_PG0_Init>=Ram_PG1_Init){               //比如说8888 6666比7777 5555
             PE_value_l.IntData=Ram_PK0_Init-Ram_PK1_Init;
             PE_value_h.IntData=Ram_PG0_Init-Ram_PG1_Init;
             Symbol_save1.IntData&=~0x0100;
	         Symbol_save1.IntData&=~0x0200;
			 symbol_diandu1=0;
          }
          else{                                         //比如说7777 6666比8888 5555
             PE_value_l.IntData=Ram_PK1_Init-Ram_PK0_Init+10000;          
             PE_value_h.IntData=Ram_PG1_Init-1-Ram_PG0_Init; 
             Symbol_save1.IntData|=0x0100;
             Symbol_save1.IntData|=0x0200;
			 symbol_diandu1=1;
          }
       }
       else{                                                                                
          if(Ram_PG0_Init>Ram_PG1_Init){               //比如说8888 5555比7777 6666
             PE_value_l.IntData=Ram_PK0_Init+10000-Ram_PK1_Init;
             PE_value_h.IntData=Ram_PG0_Init-1-Ram_PG1_Init;
             Symbol_save1.IntData&=~0x0100;
	         Symbol_save1.IntData&=~0x0200;
			 symbol_diandu1=0;
          }
          else{                                         //比如说7777 5555比8888 6666
             PE_value_l.IntData=Ram_PK1_Init-Ram_PK0_Init;          
             PE_value_h.IntData=Ram_PG1_Init-Ram_PG0_Init;
             Symbol_save1.IntData|=0x0100;
             Symbol_save1.IntData|=0x0200;
			 symbol_diandu1=1;
          }
       }
       //电度净值的计算:2.计算无功电度净值
       if(Ram_QK0_Init>=Ram_QK1_Init){                  
          if(Ram_QG0_Init>=Ram_QG1_Init){             
             QE_value_l.IntData=Ram_QK0_Init-Ram_QK1_Init;
             QE_value_h.IntData=Ram_QG0_Init-Ram_QG1_Init;
             Symbol_save1.IntData&=~0x0400;
	         Symbol_save1.IntData&=~0x0800;
			 symbol_diandu2=0;
          }
          else{                                                         
             QE_value_l.IntData=Ram_QK1_Init-Ram_QK0_Init+10000;          
             QE_value_h.IntData=Ram_QG1_Init-1-Ram_QG0_Init; 
             Symbol_save1.IntData|=0x0400;
	         Symbol_save1.IntData|=0x0800;
			 symbol_diandu2=1;
          }
       }
       else{                                                                                
          if(Ram_QG0_Init>Ram_QG1_Init){       
             QE_value_l.IntData=Ram_QK0_Init+10000-Ram_QK1_Init;
             QE_value_h.IntData=Ram_QG0_Init-1-Ram_QG1_Init;
             Symbol_save1.IntData&=~0x0400;
	         Symbol_save1.IntData&=~0x0800;
			 symbol_diandu2=0;
          }
          else{                                                    
             QE_value_l.IntData=Ram_QK1_Init-Ram_QK0_Init;          
             QE_value_h.IntData=Ram_QG1_Init-Ram_QG0_Init; 
             Symbol_save1.IntData|=0x0400;
	         Symbol_save1.IntData|=0x0800;
			 symbol_diandu2=1;
          }
       }
   //=========================================================================================
   //								Part 2 :  多次电量的累积或平均处理
   //=========================================================================================
   if(CalCount>=50) {
     for(i=0;i<6;i++) {				//为了提高测量精度,此处采用取50次电压、电流计算结果之和的平均

⌨️ 快捷键说明

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