Changeset 11061 in ntrip for trunk/BNC/src/combination
- Timestamp:
- Oct 1, 2026, 6:34:50 PM (4 weeks ago)
- Location:
- trunk/BNC/src/combination
- Files:
-
- 2 edited
-
bnccomb.cpp (modified) (4 diffs)
-
bnccomb.h (modified) (1 diff)
Legend:
- Unmodified
- Added
- Removed
-
trunk/BNC/src/combination/bnccomb.cpp
r11059 r11061 899 899 _newCorr->_satCodeBiasIF += codeCoeff * codeBiasesRefSig[frqType]; 900 900 } 901 if (codeBiasesRefSig.size() == 2) { 902 _acBiasIF[acName][prnStr.mid(0,3)] = _newCorr->_satCodeBiasIF; 903 } 904 else { 905 _acBiasIF[acName].remove(prnStr.mid(0,3)); 906 } 901 907 _newCorr->_satCodeBias._bias.clear(); 902 908 } … … 1079 1085 out.flush(); 1080 1086 } 1087 if (_method == filter) { 1088 checkBiasConsistency(epoTime, sys, out); 1089 } 1081 1090 printResults(epoTime, out, masterCorr); 1082 1091 dumpResults(epoTime, masterCorr); … … 1144 1153 if (pp->type == cmbParam::offACSat && 1145 1154 pp->AC == corrs(sys)[maxResIndex-1]->_acName && 1146 pp->prn == corrs(sys)[maxResIndex-1]->_prn .mid(0,3)) {1155 pp->prn == corrs(sys)[maxResIndex-1]->_prn) { 1147 1156 QQ_sav.Row(iPar) = 0.0; 1148 1157 QQ_sav.Column(iPar) = 0.0; … … 1174 1183 1175 1184 return success; 1185 } 1186 1187 // Check the consistency of the AC code biases with the AC clocks 1188 //////////////////////////////////////////////////////////////////////////// 1189 // An AC's clocks refer to its own clock signals; the code biases of the 1190 // reference signals refer them to the reference signals (B_IF, ionosphere- 1191 // free combination of these biases, added to the AC clocks). If the code 1192 // biases do not belong to the clocks (e.g. taken from another product), the 1193 // error B_IF is absorbed by the AC's satellite offsets. The satellite offsets 1194 // of each AC are therefore regressed against its B_IF every 5 minutes (from 1195 // 5 minutes after the start); a warning is issued (at most once per hour per 1196 // AC and system) if B_IF varies noticeably between the satellites and the 1197 // offsets clearly follow it. 1198 //////////////////////////////////////////////////////////////////////////// 1199 void bncComb::checkBiasConsistency(bncTime epoTime, char sys, QTextStream& out) { 1200 1201 const double CHECK_INT = 300.0; // [s] check interval, first check after start 1202 const unsigned MIN_SAT = 5; 1203 const double MIN_SPREAD = 0.03; // [m] minimum std. deviation of B_IF 1204 const double MIN_SLOPE = 0.3; // 0.5 expected for 2 ACs, -> 1 for more ACs 1205 const double MIN_CORR = 0.7; 1206 1207 if (!_biasCheckStart[sys].valid()) { 1208 _biasCheckStart[sys] = epoTime; 1209 _biasCheckLast[sys] = epoTime; 1210 return; 1211 } 1212 if (epoTime - _biasCheckLast[sys] < CHECK_INT) { 1213 return; 1214 } 1215 _biasCheckLast[sys] = epoTime; 1216 1217 QListIterator<cmbAC*> itAc(_ACs); 1218 while (itAc.hasNext()) { 1219 const QString& acName = itAc.next()->name; 1220 if (!_acBiasIF.contains(acName)) { 1221 continue; 1222 } 1223 const QMap<QString, double>& biasIF = _acBiasIF[acName]; 1224 1225 // satellites of this AC in the current epoch with B_IF available 1226 QVector<double> xx, yy; 1227 for (int ii = 0; ii < corrs(sys).size(); ii++) { 1228 const cmbCorr* corr = corrs(sys)[ii]; 1229 if (corr->_acName != acName || !biasIF.contains(corr->_prn.mid(0,3))) { 1230 continue; 1231 } 1232 for (int iPar = 1; iPar <= _params[sys].size(); iPar++) { 1233 const cmbParam* pp = _params[sys][iPar-1]; 1234 if (pp->type == cmbParam::offACSat && pp->AC == acName && pp->prn == corr->_prn) { 1235 xx.push_back(biasIF[corr->_prn.mid(0,3)]); 1236 yy.push_back(pp->xx); 1237 break; 1238 } 1239 } 1240 } 1241 unsigned nn = xx.size(); 1242 if (nn < MIN_SAT) { 1243 continue; 1244 } 1245 double mx = 0.0, my = 0.0; 1246 for (unsigned ii = 0; ii < nn; ii++) { 1247 mx += xx[ii] / nn; 1248 my += yy[ii] / nn; 1249 } 1250 double sxx = 0.0, syy = 0.0, sxy = 0.0; 1251 for (unsigned ii = 0; ii < nn; ii++) { 1252 sxx += (xx[ii] - mx) * (xx[ii] - mx); 1253 syy += (yy[ii] - my) * (yy[ii] - my); 1254 sxy += (xx[ii] - mx) * (yy[ii] - my); 1255 } 1256 double spread = sqrt(sxx / nn); 1257 if (spread < MIN_SPREAD || syy <= 0.0) { 1258 continue; 1259 } 1260 double slope = sxy / sxx; 1261 double corrCoeff = sxy / sqrt(sxx * syy); 1262 if (slope < MIN_SLOPE || corrCoeff < MIN_CORR) { 1263 continue; 1264 } 1265 1266 QString refSig; 1267 for (unsigned ii = 1; ii < cmbRefSig::cIF; ii++) { 1268 t_frequency::type frqType = cmbRefSig::toFreq(sys, static_cast<cmbRefSig::type>(ii)); 1269 refSig += QString("%1C%2%3").arg(ii > 1 ? "/" : "").arg(t_frequency::toString(frqType)[1]) 1270 .arg(cmbRefSig::toAttrib(sys, static_cast<cmbRefSig::type>(ii))); 1271 } 1272 QString msg = QString("%1 %2 code biases (%3) seem inconsistent with its clocks: " 1273 "satellite offsets follow the bias combination B_IF " 1274 "(%4 satellites, B_IF spread %5 m, slope %6, correlation %7)") 1275 .arg(acName).arg(sys).arg(refSig).arg(nn) 1276 .arg(spread, 0, 'f', 3).arg(slope, 0, 'f', 2).arg(corrCoeff, 0, 'f', 2); 1277 out << epoTime.datestr().c_str() << " " << epoTime.timestr().c_str() 1278 << " " << msg << "\n"; 1279 QString key = acName + sys; 1280 bncTime& warned = _biasCheckWarned[key]; 1281 if (!warned.valid() || epoTime - warned >= 3600.0) { 1282 warned = epoTime; 1283 emit newMessage("bncComb: " + msg.toLatin1(), true); 1284 } 1285 } 1176 1286 } 1177 1287 -
trunk/BNC/src/combination/bnccomb.h
r11059 r11061 270 270 QMap<QString, bncTime> _refBiasWarned; // last warning per AC and system 271 271 QMap<char, bncTime> _singleACWarned; // last 'fewer than 2 ACs' message per system 272 QMap<QString, QMap<QString, double> > _acBiasIF; // latest B_IF of the reference signals per AC and satellite 273 QMap<char, bncTime> _biasCheckStart; // first combined epoch per system 274 QMap<char, bncTime> _biasCheckLast; // last bias/clock consistency check per system 275 QMap<QString, bncTime> _biasCheckWarned; // last inconsistency warning per AC and system 276 void checkBiasConsistency(bncTime epoTime, char sys, QTextStream& out); 272 277 bool allACsBeyond(const bncTime& epoTime) const; 273 278 bncTime _resTime;
Note:
See TracChangeset
for help on using the changeset viewer.
