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

📄 cmobile.cpp

📁 这是cdma2000的一个分组调度算法实例
💻 CPP
📖 第 1 页 / 共 2 页
字号:
//////////////////////////////////////////////////////////////////////////
//                        for Evaluation Project						//
//                          Mobile User Team							//
//                      BUPT Radio Research Center						//
//////////////////////////////////////////////////////////////////////////
//																		//
//                          CMobile.CPP									//
//																		//
//////////////////////////////////////////////////////////////////////////
//																		//
// 移动台基类CMobile的成员函数的声明									//
//																		//
//																		//
// Ref. documents:														//
//          "1xEV-DV仿真程序类的初步定义"								//
//																		//
// Written by:    CAI Qi-ming, ZHANG Ding-ye,							//
//                DOU Zhong-zhao, ZHANG Xin								//
// Rev. date:     20010320 (yyyymmdd)									//
//																		//
// What's NEW:															//
//		20010319, include文件"header1.h"变为"systemsim.h",因为文件名	//
//				的可读性原因. by ZhangXin.								//
//		20020409
//				1  MobileInitialization()增加一个入口参数,放在参数列表	//
//				最后一位,代表信道类型。
//				2  MobileInitialization()中每个扇区放入规定数量的话音移
//				动台和数据移动台
//////////////////////////////////////////////////////////////////////////


#include "CMobile.h"
#include "iostream.h"
#include "Newran.h"
#include "sys_random.h" 
#include "CMsManager.h"
//#include "fstream.h"
//#include "iomanip.h"

//////////////////////////////////////////////////////////////////////////
//								初始化函数								//
//	参数有:ID,MsManager和ServiceArea的指针,运动速度,信道类型。		//
//           同时,调用其它函数,完成其它变量的初始化。					//
//////////////////////////////////////////////////////////////////////////
void CMobile::MobileInitialization(
			int           i_inputMsID, 
			CMsManager*   p_inputCMsManager, 
			CServiceArea* p_inputCServiceArea, 
			float         f_inputMsVelocity, 
			int           i_inputChannelType,
			float         f_inputStdSlowFading,
			int           i_inputTrafficType)
{
	bool bFlag=false;                     //越界标记


 	m_iMsID=i_inputMsID;                  //对MS的ID进行初始化
	m_pMsManager=p_inputCMsManager;       //MsManager指针初始化
	m_pServiceArea=p_inputCServiceArea;   //ServiceArea指针初始化
	//...... modified by cqm, Apr.9 ......//
	m_iSlotCount=1;                       //Slot记数器,设为1是因为VoiceProcess()从slot 1开始运行的
	//....................................//
	m_fStdSlowFading=f_inputStdSlowFading;//慢衰标准差
	m_nChannelType=i_inputChannelType;    
	m_fMsVelocity=f_inputMsVelocity;


	while (!bFlag)                     
	{
		LocationGenerator();           //对MS的位置坐标进行初始化     
		LocationSector();              //对MS的归属扇区标号进行初始化     
		if ((m_stLocationSector.stCellID.m==3)&&
			(m_stLocationSector.stCellID.n==3))  
		{	
			//......modified by cqm, Apr.9 .......//
			switch(i_inputTrafficType)
			{
			//如果在(3,3)小区
				case Voice : switch(m_stLocationSector.s)//产生话音用户
							{
								case 1: //m_pMsManager->m_iVoiceNumGenerated[0]++;//记录生成的话音用户数
									if(m_pMsManager->m_iVoiceNumGenerated[0]<m_pMsManager->m_iVoiceNumPerSector)//如果话音用户数目没有超标
									{
										m_pMsManager->m_iVoiceNumGenerated[0]++;//记录生成的话音用户数
										bFlag=true; //该用户有效,标志位置为真
										(m_pServiceArea->GetSector(m_stLocationSector)->m_iNumOfSector)++;//该扇区总用户数加一
									}
									break;//中断循环
								case 2: //m_pMsManager->m_iVoiceNumGenerated[1]++;//记录生成的话音用户数
									if(m_pMsManager->m_iVoiceNumGenerated[1]<m_pMsManager->m_iVoiceNumPerSector)//如果话音用户数目没有超标
									{
										m_pMsManager->m_iVoiceNumGenerated[1]++;//记录生成的话音用户数
										bFlag=true; //该用户有效,标志位置为真
										(m_pServiceArea->GetSector(m_stLocationSector)->m_iNumOfSector)++;//该扇区总用户数加一
									}
									break;//中断循环
								case 3: //m_pMsManager->m_iVoiceNumGenerated[2]++;//记录生成的话音用户数
									if(m_pMsManager->m_iVoiceNumGenerated[2]<m_pMsManager->m_iVoiceNumPerSector)//如果话音用户数目没有超标
									{
										m_pMsManager->m_iVoiceNumGenerated[2]++;//记录生成的话音用户数
										bFlag=true; //该用户有效,标志位置为真
										(m_pServiceArea->GetSector(m_stLocationSector)->m_iNumOfSector)++;//该扇区总用户数加一
									}
									break;//中断循环
								default:
									break;
							}
					break;
				case Data : switch(m_stLocationSector.s)//产生数据用户
							{
								case 1: m_pMsManager->m_iDataNumGenerated[0]++;//记录生成的数据用户数
									if(m_pMsManager->m_iDataNumGenerated[0]<=m_pMsManager->m_iDataNumPerSector)//如果数据用户数目没有超标
									{
										bFlag=true; //该用户有效,标志位置为真
										(m_pServiceArea->GetSector(m_stLocationSector)->m_iNumOfSector)++;//该扇区总用户数加一
									}
									break;//中断循环
								case 2: m_pMsManager->m_iDataNumGenerated[1]++;//记录生成的数据用户数
									if(m_pMsManager->m_iDataNumGenerated[1]<=m_pMsManager->m_iDataNumPerSector)//如果数据用户数目没有超标
									{
										bFlag=true; //该用户有效,标志位置为真
										(m_pServiceArea->GetSector(m_stLocationSector)->m_iNumOfSector)++;//该扇区总用户数加一
									}
									break;//中断循环
								case 3: m_pMsManager->m_iDataNumGenerated[2]++;//记录生成的数据用户数
									if(m_pMsManager->m_iDataNumGenerated[2]<=m_pMsManager->m_iDataNumPerSector)//如果数据用户数目没有超标
									{
										bFlag=true; //该用户有效,标志位置为真
										(m_pServiceArea->GetSector(m_stLocationSector)->m_iNumOfSector)++;//该扇区总用户数加一
									}
									break;//中断循环
								default:
									break;
							}
					break;
			}
		}
	}

	InitChannelModel(f_inputStdSlowFading,i_inputChannelType);     //对MS的信道模型数据进行初始化
   	InitNeighborSet();                  //根据MS的归属扇区对相邻扇区数组成员数据进行初始化
	InitCadidateSet();                  //根据MS的归属扇区以及相邻扇区数据对候选扇区数组进行初始化
}
//end of MobileInitialization()

	
//////////////////////////////////////////////////////////////////////////
//							坐标生成函数								//
//							随机产生移动台的坐标						//
//////////////////////////////////////////////////////////////////////////
void CMobile::LocationGenerator()
{
#ifdef UNIFORMITY
	m_stMsLocation.x
		=xUniform((float)sqrt(3)*m_pServiceArea->GetSiteDistance(),(float)(5*m_pServiceArea->GetSiteDistance()
		/sqrt(3)));     //产生的移动台的坐标服从均匀分布(只针对(3.3)的小区)
	m_stMsLocation.y
		=xUniform((float)2*m_pServiceArea->GetSiteDistance(),(float)(3*m_pServiceArea->GetSiteDistance()));
#endif


//..............................Modified By hj,  July,11,2003 ...............................//
//移动台撒在以BS为中心的圆上(只针对(3.3)的小区)
#ifdef  R1
    float m_stMsRadius=(float)0.9*m_pServiceArea->GetSiteDistance()/2;  //半径R定义为小区间距的一半,移动台分布半径分别为0.9R,0.5R,0.1R移动台分布半径
	float m_stMsCentreAngle=xUniform((float)0.0,(float)2*PI);           //随机生成移动台圆心角,圆心角在0到2PI之间均匀分布
    m_stMsLocation.x=(float)(4*m_pServiceArea->GetSiteDistance()/sqrt(3)+m_stMsRadius*cos(m_stMsCentreAngle));
    m_stMsLocation.y=(float)(2.5*m_pServiceArea->GetSiteDistance()+m_stMsRadius*sin(m_stMsCentreAngle));
#endif

#ifdef  R2
    float m_stMsRadius=(float)0.5*m_pServiceArea->GetSiteDistance()/2;  //半径R定义为小区间距的一半,移动台分布半径分别为0.9R,0.5R,0.1R移动台分布半径
	float m_stMsCentreAngle=xUniform((float)0.0,(float)2*PI);           //随机生成移动台圆心角,圆心角在0到2PI之间均匀分布
    m_stMsLocation.x=(float)(4*m_pServiceArea->GetSiteDistance()/sqrt(3)+m_stMsRadius*cos(m_stMsCentreAngle));
    m_stMsLocation.y=(float)(2.5*m_pServiceArea->GetSiteDistance()+m_stMsRadius*sin(m_stMsCentreAngle));
#endif

#ifdef  R3
    float m_stMsRadius=(float)0.1*m_pServiceArea->GetSiteDistance()/2;  //半径R定义为小区间距的一半,移动台分布半径分别为0.9R,0.5R,0.1R移动台分布半径
	float m_stMsCentreAngle=xUniform((float)0.0,(float)2*PI);           //随机生成移动台圆心角,圆心角在0到2PI之间均匀分布
    m_stMsLocation.x=(float)(4*m_pServiceArea->GetSiteDistance()/sqrt(3)+m_stMsRadius*cos(m_stMsCentreAngle));
    m_stMsLocation.y=(float)(2.5*m_pServiceArea->GetSiteDistance()+m_stMsRadius*sin(m_stMsCentreAngle));
#endif
//.............................................................................................//


}
//end of LocationGenerator()


//////////////////////////////////////////////////////////////////////////
//						  归属扇区确定函数								//
//					 通过调用ServiceArea中的函数获得					//
//////////////////////////////////////////////////////////////////////////			
void CMobile::LocationSector()
{
	m_stLocationSector=m_pServiceArea->GetUserCell(m_stMsLocation);  //调用ServiceArea的函数GetUserCell()完成归属扇区的初始化
}
//end of LocationSector()


//////////////////////////////////////////////////////////////////////////
//						   信道模型初始化函数							//
//			调用CchannelModel的初始化函数,完成信道模型的初始化			//
//////////////////////////////////////////////////////////////////////////
void CMobile::InitChannelModel(float f_inputStdSlowFading,
							   int i_inputChannelType)
{                    //定义必要的变量
	int i,j;         //循环变量


	for(i=0;i<19;i++)
		for(j=0;j<SectorNumber;j++)
		{
			m_aNeighborSector[i*SectorNumber+j].stSectorID.stCellID
				=m_pServiceArea->GetCell(m_stLocationSector.stCellID)
				->m_aNeighborCell[i]->m_stCellID;   
			//相邻扇区集的小区标号初始化
			m_aNeighborSector[i*SectorNumber+j].stSectorID.s=j+1;              
			//相邻扇区集的扇区标号初始化,扇区的标号是从1到3
		}
	m_ChannelModel.Initialization(f_inputStdSlowFading,
		i_inputChannelType,m_aNeighborSector);    //信道模型初始化
}
//end of InitChannelModel()


//////////////////////////////////////////////////////////////////////////
//					  相邻扇区信息初始化函数							//
//		从归属小区中读出相邻扇区的标号,计算路径损耗和天线增益,		//
//	    并通过CchannelModel获得快衰和慢衰的初始值,计算出总路径损耗,	//
//                  获得扇区到达移动台的干扰值。						//
//////////////////////////////////////////////////////////////////////////
void CMobile::InitNeighborSet()
{                                               //定义必要的变量
	int i,j,k;
	float fMsBsDistance;                        //基站和MS的距离,单位是米
	float fTempPathLoss;                        //路径损耗
	float fMsxAngel;                            //MS与x轴的夹角,范围0到2*PI
	float fSectorMsAngel;                       //MS与扇区的夹角,范围-PI到PI
	float fTempAngel;
	float fTempAntennaGain;                     //天线增益
	CCell* pCell=NULL;                          //指向相邻集中一个小区的指针
	LOCATION_TYPE stNeighborCellCor;            //邻小区基站坐标
	
	m_pFadingValuePointer=m_ChannelModel.GetFadingValues(m_iSlotCount); //获得衰落数组(初始值)的首地址
	pCell=m_pServiceArea->GetCell(m_stLocationSector.stCellID);           
	//获得MS所在小区的指针
	for(i=0;i<19;i++)                 //循环19次(相邻a集小区的个数)
	{
		stNeighborCellCor=pCell->m_aNeighborCellLocation[i];               //第i个邻小区的坐标(实际上是BS的坐标)
		fMsBsDistance=(float)(sqrt(pow((m_stMsLocation.x
			-stNeighborCellCor.x),2)+pow((m_stMsLocation.y
			-stNeighborCellCor.y),2)));   //计算BS和MS的直线距离

        fTempPathLoss=-(float)(28.6+35*log10(1000*fMsBsDistance));        
			//计算路径损耗,单位是dB(参考C50-20000918-011, 
			//"Evaluation Methods for High Speed Forward Link Packet Access,"
			//September 20, 2000.)
		if(fTempPathLoss>-82.6)                       //最小路径损耗是-82.6dB
			fTempPathLoss=(float)-82.6;
		fTempPathLoss=(float)pow(10,(fTempPathLoss/10));               
			//转换为倍数

		fMsxAngel=(float)(atan2((m_stMsLocation.y-stNeighborCellCor.y),
			(m_stMsLocation.x-stNeighborCellCor.x)));
			//MS与x轴的夹角,范围-PI到PI
		if(fMsxAngel<0)                                          
			//将角度的范围转化到0到2*PI
			fMsxAngel=(float)(fMsxAngel+2*PI); 
		
		for(j=0;j<SectorNumber;j++)                   
		{
			m_aNeighborSector[i*SectorNumber+j].fPathLoss=fTempPathLoss;            //小区的路径损耗值初始化
			fTempAngel
				=(float)(fMsxAngel-pCell->m_aSectorInCell[j].
				GetSectorOrientation()*2*PI/360);   //转化为弧度来算

			if(fTempAngel>=PI)               //若差值大于等于PI,则换算
				fSectorMsAngel=(float)(fTempAngel-2*PI);
			else 
				if(fTempAngel<-PI)       //若差值小于-PI,也换算
					fSectorMsAngel=(float)(fTempAngel+2*PI);
				else 
					fSectorMsAngel=fTempAngel;    
						//否则就取差值作为扇区朝向与MS的夹角

			fTempAntennaGain=AntennaGain-20;      //天线增益,单位dB
			if(12*pow((fSectorMsAngel/(70*2*PI/360)),2)<20)        
				//公式参考《关于服务区环境模型的一些初步设想》
				fTempAntennaGain=(float)(AntennaGain
				-12*pow((fSectorMsAngel/(70*2*PI/360)),2));
			fTempAntennaGain=(float)pow(10,(fTempAntennaGain/10));        
				//转换为倍数

			m_aNeighborSector[i*SectorNumber+j].fAntennaGain
				=fTempAntennaGain;                //天线增益初始化
			m_aNeighborSector[i*SectorNumber+j].fSlowFading
				=m_pFadingValuePointer[i].fSlowFading;          //慢衰值初始化
			for(k=0;k<SubslotNumber;k++)
				m_aNeighborSector[i*SectorNumber+j].fFastFading[k]
					=m_pFadingValuePointer[i].fFastFadingSet[j][k];
			m_aNeighborSector[i*SectorNumber+j].fPropagationLoss
				=m_aNeighborSector[i*SectorNumber+j].fPathLoss
				*m_aNeighborSector[i*SectorNumber+j].fAntennaGain
				*m_aNeighborSector[i*SectorNumber+j].fSlowFading
				*(float)pow(10,(MsAntennaGain-OtherLosses)/10);  
				//总的损耗值
			m_aNeighborSector[i*SectorNumber+j].fPowerFromTheSector
				=m_pServiceArea
				->GetSector(m_aNeighborSector[i*SectorNumber+j].stSectorID)
				->GetTxPower()
				*m_aNeighborSector[i*SectorNumber+j].fPropagationLoss
				*(m_aNeighborSector[i*SectorNumber+j].fFastFading[0]
				+m_aNeighborSector[i*SectorNumber+j].fFastFading[1]
				+m_aNeighborSector[i*SectorNumber+j].fFastFading[2]
				+m_aNeighborSector[i*SectorNumber+j].fFastFading[3])/(float)4;    
				//扇区到达移动台的总功率为=发射功率*总的损耗
		}
	}
}
//end of InitNeighborSet()


//////////////////////////////////////////////////////////////////////////
//						 候选扇区信息初始化函数							//
//			从归属小区读出候选扇区的标号,确定自己的相邻扇区在			//
//			相邻扇区信息数组中的相对位置(数组下标),完成干扰、		//
//			功率、信噪比的初始计算,复位定时器。						//
//////////////////////////////////////////////////////////////////////////
void CMobile::InitCadidateSet()
{                                 //定义必要的变量
	int i,j,k,m;                  //循环变量
	float fOtherChannelPower;     //其他信道的干扰值,单位:mw
	float fOrthogonalFactor;      //正交因子
	float fFastFading;            //快衰(四个子时隙的算术平均)
	CCell* pMsCell=NULL;          //移动台所在小区指针
	CELLID_TYPE stTempCell;       //临时小区结构体


	for(i=0;i<6+SectorNumber;i++)                    //第i个候选扇区
	{
		k=0;
		m_aCandidateSector[i].fInterferenceFromOtherSector=0;               
		//初始化从其他扇区来的干扰值
		pMsCell=m_pServiceArea->GetCell(m_stLocationSector.stCellID);       
		//得到MS所在的小区
		m_aCandidateSector[i].stSectorID.stCellID
			=pMsCell->m_aCandidateSector[i]->GetParentCellID();    
		//将属性中的候选扇区的标号初始化
		m_aCandidateSector[i].stSectorID.s
			=pMsCell->m_aCandidateSector[i]->GetSectorIndex();

		for(j=0;j<19*SectorNumber;j++)
		{
			if((m_aCandidateSector[i].stSectorID.stCellID.m
				==m_aNeighborSector[j].stSectorID.stCellID.m)
				&&(m_aCandidateSector[i].stSectorID.stCellID.n
				==m_aNeighborSector[j].stSectorID.stCellID.n)
				&&(m_aCandidateSector[i].stSectorID.s

⌨️ 快捷键说明

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