/// <summary> /// 供计算点路损时使用 /// </summary> /// <param name="structAntennaParam"></param> /// <param name="peakTempValue"></param> public void ConvertPolarToXY(StructAntennaParam structAntennaParam, PeakTempValue peakTempValue) { if (peakTempValue.PeakDot != 0) { float horizonAzimuth = CalculateHorizontalAzimuth(structAntennaParam.CellX, structAntennaParam.CellY, structAntennaParam.MsX, structAntennaParam.MsY); float distanceFromTxToPeak = peakTempValue.PeakDot * peakTempValue.Resolution; TransPolarToXYHelper(structAntennaParam, horizonAzimuth, distanceFromTxToPeak); } }
/// <summary> /// 计算点到点的绕射损耗值 /// </summary> /// <param name="altitudes">点到点连线上相关点集的海拔信息</param> /// <param name="distance">点到点的距离</param> /// <param name="buildHeights">点到点连线上相关点集的建筑物高度信息</param> /// <param name="clutterTypeIDs"></param> /// <returns>绕射损耗的值</returns> public float GetPTPDiffractionLoss(short[] altitudes, float distance, short[] buildHeights, short[] clutterTypeIDs,PeakTempValue peakTempValue) { int nBinNum = altitudes.Length - 1;//海拔信息的一组点的数目 if (nBinNum >= 2) { this.BuildingCalculate(altitudes, ref buildHeights, nBinNum, clutterTypeIDs); float txHeight = this.CalculateTxHeights(this.m_DifLossCalcPara, buildHeights)[0] + altitudes[0];//发射天线自高+海拔高度 float rxHeight = 0f; rxHeight = this.CalcRxHeight(buildHeights, ref rxHeight, nBinNum, altitudes, clutterTypeIDs); float txToRxLen = (buildHeights.Length - 1) * this.m_DifLossCalcPara.CalcResolution;//发射点到接收点的直线水平距离 float txToRxLineLen = (float)Math.Sqrt((double)((txToRxLen * txToRxLen) + ((txHeight - rxHeight) * (txHeight - rxHeight))));//发射点到接受点的直线距离 int[] buildPeakHeightIDs = ProfileEdges.SearchPeaks(buildHeights);//需要计算绕射损耗的高度点的id的集合? if (buildPeakHeightIDs.Length == 0) { return 0f; } //需要计算绕射损耗的点的ID集合 List<int> buildPeakHeightIDList = new List<int>(); for (int i = 0; i < buildPeakHeightIDs.Length; i++) { float peakHeight = buildHeights[buildPeakHeightIDs[i]]; float txToPeakLevelDistance = this.m_DifLossCalcPara.CalcResolution * buildPeakHeightIDs[i];//发射点到中断点的水平距离 float peakToRxLevelDistance = txToRxLen - txToPeakLevelDistance;//中断点到接受点的水平距离 if (this.IsInFres(peakHeight, txToPeakLevelDistance, peakToRxLevelDistance, txHeight, rxHeight, txToRxLineLen)) { buildPeakHeightIDList.Add(buildPeakHeightIDs[i]); } } if (buildPeakHeightIDList.Count > 0) { int[] peaks = this.GetHFactorTop3Peaks(buildHeights, buildPeakHeightIDList.ToArray(), txHeight, rxHeight, txToRxLen, this.m_DifLossCalcPara.CalcResolution); ////获得基站和移动台间遮挡物信息 short mountHeight = 0; int dotPeakIndex = 0; int factor = 0; for (int i = 0; i < peaks.Length; i++)//选取基站至移动台之间的最高峰 { if (mountHeight < buildHeights[peaks[i]]) { mountHeight += buildHeights[peaks[i]]; dotPeakIndex += peaks[i]; factor++; } } peakTempValue.PeakHeight = (short)(mountHeight / (float)(factor * 2f)); peakTempValue.PeakDot = (short)(dotPeakIndex / (factor * 2f)); return this.EdgeLossSelect(buildHeights, peaks, txHeight, rxHeight, txToRxLen, txToRxLineLen); } } return 0f; }
/// <summary> /// 计算绕射损耗 /// </summary> /// <param name="distance"></param> /// <param name="index"></param> /// <returns></returns> public float CalcDiffLoss(float distance, int index, PeakTempValue peakTempValue) { //没有选择绕射损耗计算方法则不计算绕射损耗值 if (m_SectionPathLossCalcParam.PropagModel.DifLossMethod == null) { return 0f; } short[] destinationArray = new short[index]; short[] buildHeights = new short[index]; short[] clutterTypeIDs = new short[index]; Array.Copy(m_AltitudeHeights, destinationArray, index); Array.Copy(m_BuildHeights, buildHeights, index); Array.Copy(m_ClutterTypeIDs, clutterTypeIDs, index); return m_DiffractionLossCalulator.GetPTPDiffractionLoss(destinationArray, distance, buildHeights, clutterTypeIDs, peakTempValue); }
//public override float[] CalculateRayPathLoss(RayMethodParam param, IPropagationModel model, ref bool isStopCalculator) //{ // OkumuHataPropagationModel okumuHataPropagationModel = model as OkumuHataPropagationModel; // float f = param.Frequency; // int startIndex = param.StartIndex; // int endIndex = param.EndIndex; // float calcResolution = param.CalcResolution; // float[] txEffHeight = param.TxEffHeight; // float[] rxEffHeight = param.RxEffHeight; // float[] numArray3 = new float[(endIndex - startIndex) + 1]; // if (okumuHataPropagationModel != null) // { // float num8 = this.CellSelect(f, okumuHataPropagationModel); // float num7 = (float) Math.Log10((double) f); // float num6 = (float) Math.Log10((double) txEffHeight[0]); // StructAntennaParam antennaGainParam = param.AntennaGainParam; // for (int i = 0; i < numArray3.Length; i++) // { // if (isStopCalculator) // { // return numArray3; // } // if ((param.TxEffHeight[i] != -32768f) && (param.RxEffHeight[i] != -32768f)) // { // float num5 = this.GetDistance(startIndex, i, calcResolution); // float num11 = this.AhrCalculate(f, rxEffHeight, i, okumuHataPropagationModel); // float num9 = (i + startIndex) * calcResolution; // float num12 = base.CalcDiffLoss(i * calcResolution, i); // float num13 = ((((okumuHataPropagationModel.K1 + (okumuHataPropagationModel.K2 * num7)) - (okumuHataPropagationModel.K3 * num6)) + ((okumuHataPropagationModel.K4 - (okumuHataPropagationModel.K5 * num6)) * num5)) + num11) + num8; // numArray3[i] = num13 + (num12 * okumuHataPropagationModel.KDiffraction); // string message = string.Concat(new object[] { // DateTime.Now.ToString("G"), ",", param.CellName, ",", param.X, ",", param.Y, ",", txEffHeight[0], ",", param.RxEffHeight[i], ",", okumuHataPropagationModel.PropModelName, ",", base.m_RayIndex, ",", // i, ",", calcResolution, ",,,", num12, ",", num13, ",", numArray3[i] // }); // if (base.m_Log4net.IsDebugEnabled) // { // base.m_Log4net.Debug(message); // } // } // else // { // numArray3[i] = float.MinValue; // } // } // } // return numArray3; //} #endregion #region modified 2012.9.24 public override float[] CalculateRayPathLoss(RayMethodParam param, IPropagationModel model, ref bool isStopCalculator) { OkumuHataPropagationModel okumuHataPropagationModel = model as OkumuHataPropagationModel; float f = param.Frequency; int startIndex = param.StartIndex; int endIndex = param.EndIndex; float calcResolution = param.CalcResolution; float[] txEffHeight = param.TxEffHeight; float[] rxEffHeight = param.RxEffHeight; float[] numArray3 = new float[(endIndex - startIndex) + 1]; param.PeakHeightMatrix = new short[(endIndex - startIndex) + 1]; param.PeakDotMatrix = new int[(endIndex - startIndex) + 1]; PeakTempValue peakTempValue = new PeakTempValue(); if (okumuHataPropagationModel != null) { float num8 = this.CellSelect(f, okumuHataPropagationModel); float num7 = (float)Math.Log10((double)f); float num6 = (float)Math.Log10((double)txEffHeight[0]); StructAntennaParam antennaGainParam = param.AntennaGainParam; for (int i = 0; i < numArray3.Length; i++) { if (isStopCalculator) { return numArray3; } if ((param.TxEffHeight[i] != -32768f) && (param.RxEffHeight[i] != -32768f)) { float num5 = this.GetDistance(startIndex, i, calcResolution); float num11 = this.AhrCalculate(f, rxEffHeight, i, okumuHataPropagationModel); float num9 = (i + startIndex) * calcResolution; float num12 = base.CalcDiffLoss(i * calcResolution, i, peakTempValue); param.PeakDotMatrix[i] = (int)peakTempValue.PeakDot; param.PeakHeightMatrix[i] = peakTempValue.PeakHeight; float num13 = ((((okumuHataPropagationModel.K1 + (okumuHataPropagationModel.K2 * num7)) - (okumuHataPropagationModel.K3 * num6)) + ((okumuHataPropagationModel.K4 - (okumuHataPropagationModel.K5 * num6)) * num5)) + num11) + num8; numArray3[i] = num13 + (num12 * okumuHataPropagationModel.KDiffraction); string message = string.Concat(new object[] { DateTime.Now.ToString("G"), ",", param.CellName, ",", param.X, ",", param.Y, ",", txEffHeight[0], ",", param.RxEffHeight[i], ",", okumuHataPropagationModel.PropModelName, ",", base.m_RayIndex, ",", i, ",", calcResolution, ",,,", num12, ",", num13, ",", numArray3[i] }); if (base.m_Log4net.IsDebugEnabled) { base.m_Log4net.Debug(message); } } else { numArray3[i] = float.MinValue; } } } return numArray3; }
/// <summary> /// 计算射线上的点的路径损耗 /// </summary> /// <param name="param"></param> /// <param name="model"></param> /// <param name="isStopCalculator"></param> /// <returns></returns> public override float[] CalculateRayPathLoss(RayMethodParam param, IPropagationModel model, ref bool isStopCalculator) { Dictionary<GeoXYPoint, float> results = new Dictionary<GeoXYPoint, float>(); ITUR230PropagationModel ITUR230PropModel = model as ITUR230PropagationModel; float frequency = param.Frequency;//频率 float height = param.AntHeight;//基站高度 // float height = 0; int startIndex = param.StartIndex; param.PeakHeightMatrix = new short[(param.EndIndex - startIndex) + 1]; param.PeakDotMatrix = new int[(param.EndIndex - startIndex) + 1]; PeakTempValue peakTempValue = new PeakTempValue(); GeoXYPoint sitePoint = new GeoXYPoint(param.X, param.Y); float[] pointsPathLossOnRay = new float[(param.EndIndex - startIndex) + 1]; if (ITUR230PropModel != null) { float calcResolution = param.CalcResolution; for (int i = 0; i < pointsPathLossOnRay.Length; i++) { if (isStopCalculator) return pointsPathLossOnRay; if ((param.TxEffHeight[i] != -32768f) && (param.RxEffHeight[i] != -32768f)) { GeoXYPoint calPoint = new GeoXYPoint(param.X + (i + startIndex) * param.CalcResolution * Math.Sin(param.Angle), param.Y + (i + startIndex) * param.CalcResolution * Math.Cos(param.Angle)); double distance = GetDistance(calPoint, sitePoint);//每个点到基站的距离 param.PeakHeightMatrix[i] = peakTempValue.PeakHeight; param.PeakDotMatrix[i] = (int)peakTempValue.PeakDot; //pointsPathLossOnRay[i] = CalculatePointPathLossOnRayByITUR230(height, frequency, distance, ref isStopCalculator);//每个点到基站的路损计算 pointsPathLossOnRay[i] = (float)getLoss(230, distance / 1000, height, 10, 10) - k1;//getLoss(Double frequence, Double distance, Double height, Double G, Double Heff) //frequence:频率,distance:距离,height:天线高度,G:天线增益,单位dB ,Heff:附近环境的平均高度,通过Gis获得?(典型场景:中心城市30m,郊区20m,农村10m?) results.Add(calPoint, pointsPathLossOnRay[i]); } } } return pointsPathLossOnRay; }