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

📄 dongzhiopti.cpp

📁 石油公司网管系统优化系统软件源码,很有价值的.
💻 CPP
📖 第 1 页 / 共 5 页
字号:
//---------------------------------------------------------------------------

#include <vcl.h>
#pragma hdrstop

#include "DongZhiOpti.h"

#include <math.h>
//---------------------------------------------------------------------------
#pragma package(smart_init)
#pragma resource "*.dfm"
TTDongZhiOpti *TDongZhiOpti;
//---------------------------------------------------------------------------
__fastcall TTDongZhiOpti::TTDongZhiOpti(TComponent* Owner)
    : TForm(Owner)
{
    Terminated=false;
}
//---------------------------------------------------------------------------
void __fastcall TTDongZhiOpti::TimerTimer(TObject *Sender)
{
    Timer->Enabled=false;
    Execute();
    ModalResult=mrOk;
}
//---------------------------------------------------------------------------


double TTDongZhiOpti::GetYaJiang(double G,double T,double Pz,
        double QiYouBi,double HanShuiLv,double d,double L,double GaoCha)
{
    double Q0,ql,Ql,Qg,Rs,B,QiMiDu,YouMiDu,Pr,_P,HL0,HL,TiJiHanYe,TiJiHanQi,HunHeliuSu,A;
    double QiNianDu,YouNianDu,YeNianDu,TiJiHanShui,HunHeNianDu,HunHeMiDu,ShuiMiDu,YeMiDu;
    double Z,C,S0,MoZuXiShu,ShuiPingYaJiang,GaoChengYaJiang,QiZheSuanLiuSu,Gl,YaJiang;
    double Tr,Prr,HunHeLiuSu,Re,Fe,Trr;
    L*=1e-3;
    Pr=Pz+1000;;
    int i;
    for(i=0;i<100;i++)
    {
        _P=(Pr+Pz)/2;
        //气液密度
        QiMiDu=WuXing.GetQiMiDu(T,_P);
        if(QiMiDu==0)
        {
            Application->MessageBox("天然气密度计算错误!计算中止!", "错误", MB_OK);
            Terminate();
            return 0;
        }
        YouMiDu=WuXing.GetYouMiDu(T);
        //气液流量
        Q0=G/YouMiDu;
        ql=Q0/(1-HanShuiLv);
        Rs=WuXing.GetRs(YouMiDu,_P,T);
        if(Rs>QiYouBi)
        {
            Application->MessageBox("天然气溶解系数大于气油比!计算中止!", "错误", MB_OK);
            Terminate();
            return 0;
        }
        B=WuXing.GetB(Rs,YouMiDu,T);
        Ql=ql*B;
        Trr=(T+273.15)/264.87;
        Prr=(_P)/(43.960*1e5);
        Z=WuXing.GetZ(Prr,Trr);
        if(Z==0)
        {
            Application->MessageBox("天然气压缩系数计算错误!计算中止!", "错误", MB_OK);
            Terminate();
            return 0;
        }
//        Qg=ql*(QiYouBi*G/Q0-Rs)*0.101*T*Z/(_P*20);
        Qg=ql*(QiYouBi-Rs)*101325*(T+273.15)*Z/(_P*273.15);
        //体积含液
        TiJiHanYe=Ql/(Ql+Qg);
        TiJiHanQi=1-TiJiHanYe;
        ShuiMiDu=WuXing.GetShuiMiDu(T);
        //液相密度
        YeMiDu=ShuiMiDu*HanShuiLv+YouMiDu*(1-HanShuiLv);
        YeMiDu=(YeMiDu+QiXiangDuiMiDu*1.205*Rs)/B;
        //混合流速
        HunHeLiuSu=4*(Ql+Qg)/(M_PI*d*d);
        //气油粘度
        QiNianDu=WuXing.GetQiNianDu(QiMiDu,T);
        YouNianDu=WuXing.GetYouNianDu(T);
        if(YouNianDu==0)
        {
            Application->MessageBox("粘度计算错误,计算终止!", "错误", MB_OK);
            Terminate();
            return 0;
        }
        //液相粘度
        TiJiHanShui=(HanShuiLv/ShuiMiDu)/(HanShuiLv/ShuiMiDu+(1-HanShuiLv)/YouMiDu);
        if(TiJiHanShui<0.7)
        {
            YeNianDu=YouNianDu*exp(4*TiJiHanShui);
        }
        else
        {
            YeNianDu=YouNianDu*exp(6.5*TiJiHanShui);
        }
        //混合粘度
        HunHeNianDu=QiNianDu*TiJiHanQi+YeNianDu*TiJiHanYe;
        HL=TiJiHanYe;
        //循环确定截面含液率
        do
        {
            HL0=HL;
            //混合物密度
            HunHeMiDu=YeMiDu*TiJiHanYe*TiJiHanYe/HL0+QiMiDu*TiJiHanQi*TiJiHanQi/(1-HL0);
            //雷诺数
            Re=d*HunHeLiuSu*HunHeMiDu/HunHeNianDu;
            //查图求截面含液率
            HL=WuXing.GetHL(Re,TiJiHanYe);
            if(HL==-1)
            {
                Application->MessageBox("持液率计算错误,计算终止!", "错误", MB_OK);
                Terminate();
                return 0;
            }
        }while(fabs(HL-HL0)/HL>0.05);
        //阻力系数
        C=log(TiJiHanYe);
        S0=1.281+0.478*C+0.444*C*C+0.094*C*C*C+0.00843*C*C*C*C;
        C=1-C/S0;
        MoZuXiShu=C*(0.0056+0.5/pow(Re,0.32));
        //计算水平压降
        ShuiPingYaJiang=MoZuXiShu*HunHeLiuSu*HunHeLiuSu*L*HunHeMiDu*1e-3/(2*d);
        //计算因高程产生的压降
        A=M_PI*d*d/4;
        QiZheSuanLiuSu=Qg/A;
        if(QiZheSuanLiuSu<=15)
        {
            Fe=1/(1+1.0785*pow(QiZheSuanLiuSu,1.006));
        }
        else
        {
            Gl=YeMiDu*Ql;
            Fe=3.175*1e-5*sqrt(Gl/A)/pow(QiZheSuanLiuSu,0.7);
        }
        GaoChengYaJiang=Fe*YeMiDu*g*GaoCha/1e6;
        //总压将
        YaJiang=ShuiPingYaJiang+GaoChengYaJiang;
        YaJiang*=1e6;
        //判断精度
        if(fabs(Pr-Pz-YaJiang)/YaJiang<0.05)
        {
            Pr=Pz+YaJiang;
            break;
        }
        Pr=Pz+YaJiang;
    }
    return Pr;
}

void TTDongZhiOpti::BuJuJieGuo()
{
    WellUnit *Well,*CurrentWell,*TempWell,*TempPreWell,*BaseWell,*PreWell;
    WellHead *CurrentHead=Head,*TempHead,*CurrentTemp;
    int TempInt,i;
    AnsiString TempStr;
    TFileStream *File;
    //总体结果
//    File=new TFileStream("OverView2.dat",fmCreate|fmOpenWrite|fmShareExclusive);
    ADOResult->TableName="over";
    ADOResult->Open();
    ADOResult->First();
    //油井位置
    ADOResult->MoveBy(2);
//    TempInt=2;
//    File->Write(&TempInt,sizeof(int));
    //总耗钢量
//    File->Write(&(BestUnit->Fitness),sizeof(double));
    ADOResult->Edit();
    ADOResult->FieldByName("耗钢量")->AsFloat=BestUnit->Fitness;
    //总输量
    ADOResult->FieldByName("流量")->AsFloat=Head->YouLiuLiang;
//    File->Write(&(Head->YouLiuLiang),sizeof(double));
    //增压点个数
    TempInt=0;
    for(i=0;i<GenNum;i++)
    {
        if(StationFlag[i]==1)
        {
            TempInt++;
        }
    }
    ADOResult->FieldByName("增压点")->AsInteger=TempInt;
    //File->Write(&TempInt,sizeof(int));
    //转油站个数
    TempInt=0;
    for(i=0;i<GenNum;i++)
    {
        if(StationFlag[i]==2)
        {
            TempInt++;
        }
    }
    ADOResult->FieldByName("转油站")->AsInteger=TempInt;
    ADOResult->Post();
//    File->Write(&TempInt,sizeof(int));
//    delete File;
    ADOResult->Close();
    File=new TFileStream("Dong.pos",fmCreate|fmOpenWrite|fmShareExclusive);
//    ZuoBiao=new TFileStream("ZuoBiao2.dat",fmCreate|fmOpenWrite|fmShareExclusive);
/*
    //标识位,0-油井,1-增压点,2-转油站,3-联合站
    TempInt=3;
    File->Write(&TempInt,sizeof(int));
*/
    //编号
    TempStr=Head->No;
    TempInt=TempStr.Length();
    File->Write(&TempInt,sizeof(int));
    File->Write(TempStr.c_str(),TempStr.Length());
    //新建?
    TempInt=0;
    File->Write(&TempInt,sizeof(int));
    //联合站坐标
    File->Write(&(BestUnit->Gens[2*GenNum-2]),sizeof(double));
    File->Write(&(BestUnit->Gens[2*GenNum-1]),sizeof(double));
    Head->X=BestUnit->Gens[2*GenNum-2];
    Head->Y=BestUnit->Gens[2*GenNum-1];
    CurrentHead=Head->Next;
/*
    double x_max,x_min,y_max,y_min;
    x_min=x_max=CurrentHead->Well->X;
    y_min=y_max=CurrentHead->Well->Y;
    while(CurrentHead!=0)
    {
        TempHead=CurrentHead->Sub;
        while(TempHead!=0)
        {
            Well=TempHead->Well;
            while(Well!=0)
            {
                if(Well->X<x_min)
                {
                    x_min=Well->X;
                }
                if(Well->Y<y_min)
                {
                    y_min=Well->Y;
                }
                if(Well->X>x_max)
                {
                    x_max=Well->X;
                }
                if(Well->Y>y_max)
                {
                    y_max=Well->Y;
                }
                Well=Well->Next;
            }
            TempHead=TempHead->Sub;
        }
        Well=CurrentHead->Well;
        while(Well!=0)
        {
            if(Well->X<x_min)
            {
                x_min=Well->X;
            }
            if(Well->Y<y_min)
            {
                y_min=Well->Y;
            }
            if(Well->X>x_max)
            {
                x_max=Well->X;
            }
            if(Well->Y>y_max)
            {
                y_max=Well->Y;
            }
            Well=Well->Next;
        }
        CurrentHead=CurrentHead->Next;
    }
//    ZuoBiao->Write(&x_min,sizeof(double));
//    ZuoBiao->Write(&x_max,sizeof(double));
//    ZuoBiao->Write(&y_min,sizeof(double));
//    ZuoBiao->Write(&y_max,sizeof(double));
*/
    CurrentHead=Head->Next;
    i=0;
    while(CurrentHead!=0)
    {
        //标识位,0-油井,1-增压点,2-转油站,3-联合站
        TempInt=2;
        File->Write(&TempInt,sizeof(int));
        //转油站编号
        TempStr=CurrentHead->No;
        //编号所占字节数
        TempInt=TempStr.Length();
        File->Write(&TempInt,sizeof(int));
        File->Write(TempStr.c_str(),TempStr.Length());
        //新建?
        TempInt=0;
        File->Write(&TempInt,sizeof(int));
        Well=CurrentHead->Well;
        while(Well!=0)
        {
            //标识位
            TempInt=0;
            File->Write(&TempInt,sizeof(int));
            //油井编号
            TempInt=Well->No.Length();
            File->Write(&TempInt,sizeof(int));
            File->Write(Well->No.c_str(),Well->No.Length());
            Well=Well->Next;
        }
        TempHead=CurrentHead->Sub;
        while(TempHead!=0)
        {
            //标识位,0-油井,1-增压点,2-转油站,3-联合站
            TempInt=1;
            File->Write(&TempInt,sizeof(int));
            //增压点编号
            TempStr=TempHead->No;
            //编号所占字节数
            TempInt=TempStr.Length();
            File->Write(&TempInt,sizeof(int));
            File->Write(TempStr.c_str(),TempStr.Length());
            //坐标
            TempHead->X=BestUnit->Gens[2*i];
            TempHead->Y=BestUnit->Gens[2*i+1];
            i++;
            Well=TempHead->Well;
            while(Well!=0)
            {
                //标识位
                TempInt=0;
                File->Write(&TempInt,sizeof(int));
                //油井编号
                TempInt=Well->No.Length();
                File->Write(&TempInt,sizeof(int));
                File->Write(Well->No.c_str(),Well->No.Length());
                Well=Well->Next;
            }
            TempHead=TempHead->Sub;
        }
        CurrentHead->X=BestUnit->Gens[2*i];
        CurrentHead->Y=BestUnit->Gens[2*i+1];
        i++;
        CurrentHead=CurrentHead->Next;
    }
    delete File;
}
//杂交
void TTDongZhiOpti::Cross(long generation)
{
    double P;
    int i,j,n,pos,Num=2*GenNum;
    for(i=0;i<popsize;i++)
    {
        if(Terminated)
        {
            return;
        }
        //确定交叉率
        P=(rand()%1000)/1000.0;
        if(P<PCross)
        {
            if(generation%2==1)
            {
                //普通交叉
                //随机确定与当前染色体交叉的染色体序号
                while((n=rand()%popsize)==i);
                //确定交叉位置
                pos=rand()%Num;
                //单点交叉
                for(j=0;j<pos;j++)
                {
                    NewPop[NewPopsize].Gens[j]=population[i].Gens[j];
//                    NewPop[NewPopsize].Limit[j]=population[i].Limit[j];
                    NewPop[NewPopsize+1].Gens[j]=population[n].Gens[j];
//                    NewPop[NewPopsize+1].Limit[j]=population[n].Limit[j];
                }
                for(j=pos;j<Num;j++)
                {
                    NewPop[NewPopsize].Gens[j]=population[n].Gens[j];
//                    NewPop[NewPopsize].Limit[j]=population[n].Limit[j];
                    NewPop[NewPopsize+1].Gens[j]=population[i].Gens[j];
//                    NewPop[NewPopsize+1].Limit[j]=population[i].Limit[j];
                }
            }
            else
            {
                //优势交叉
                //确定交叉位置
                pos=rand()%Num;
                //单点交叉
                for(j=0;j<pos;j++)
                {
                    NewPop[NewPopsize].Gens[j]=population[i].Gens[j];
//                    NewPop[NewPopsize].Limit[j]=population[i].Limit[j];

⌨️ 快捷键说明

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