IT++ Logo
llr.h
Go to the documentation of this file.
1 
29 #ifndef LLR_H
30 #define LLR_H
31 
32 #include <limits>
33 #include <itpp/base/vec.h>
34 #include <itpp/base/mat.h>
35 #include <itpp/base/specmat.h>
36 #include <itpp/base/matfunc.h>
37 #include <limits>
38 #include <itpp/itexports.h>
39 
40 namespace itpp
41 {
42 
46 typedef signed int QLLR;
47 
52 
57 
61 const QLLR QLLR_MAX = (std::numeric_limits<QLLR>::max() >> 4);
62 // added some margin to make sure the sum of two LLR is still permissible
63 
124 class ITPP_EXPORT LLR_calc_unit
125 {
126 public:
128  LLR_calc_unit();
129 
135  LLR_calc_unit(short int Dint1, short int Dint2, short int Dint3);
136 
165  void init_llr_tables(short int Dint1 = 12, short int Dint2 = 300,
166  short int Dint3 = 7);
167 
169  QLLR to_qllr(double l) const;
170 
172  QLLRvec to_qllr(const vec &l) const;
173 
175  QLLRmat to_qllr(const mat &l) const;
176 
178  double to_double(QLLR l) const;
179 
181  vec to_double(const QLLRvec &l) const;
182 
184  mat to_double(const QLLRmat &l) const;
185 
191  inline QLLR jaclog(QLLR a, QLLR b) const;
192  // Note: a version of this function taking "double" values as input
193  // is deliberately omitted, because this is rather slow.
194 
203  QLLR Boxplus(QLLR a, QLLR b) const;
204 
210  inline QLLR logexp(QLLR x) const;
211 
213  ivec get_Dint();
214 
216  friend ITPP_EXPORT std::ostream &operator<<(std::ostream &os, const LLR_calc_unit &l);
217 
218 private:
220  ivec construct_logexp_table();
221 
223  ivec logexp_table;
224 
226  short int Dint1, Dint2, Dint3;
227 };
228 
233 ITPP_EXPORT std::ostream &operator<<(std::ostream &os, const LLR_calc_unit &lcu);
234 
235 
236 // ----------------------------------------------------------------------
237 // implementation of some inline functions
238 // ----------------------------------------------------------------------
239 
240 inline double LLR_calc_unit::to_double(QLLR l) const
241 {
242  return static_cast<double>(l) / (1 << Dint1);
243 }
244 
245 inline QLLR LLR_calc_unit::to_qllr(double l) const
246 {
247  double QLLR_MAX_double = to_double(QLLR_MAX);
248  // Don't abort when overflow occurs, just saturate the QLLR
249  if (l > QLLR_MAX_double) {
250  it_info_debug("LLR_calc_unit::to_qllr(): LLR overflow");
251  return QLLR_MAX;
252  }
253  if (l < -QLLR_MAX_double) {
254  it_info_debug("LLR_calc_unit::to_qllr(): LLR overflow");
255  return -QLLR_MAX;
256  }
257  return static_cast<QLLR>(std::floor(0.5 + (1 << Dint1) * l));
258 }
259 
260 
262 {
263  it_assert_debug(x >= 0, "LLR_calc_unit::logexp(): Wrong LLR value");
264  int ind = x >> Dint3;
265  if (ind >= Dint2) // outside table
266  return 0;
267 
268  it_assert_debug(ind >= 0, "LLR_calc_unit::logexp(): Internal error");
269  it_assert_debug(ind < Dint2, "LLR_calc_unit::logexp(): internal error");
270 
271  // With interpolation
272  // int delta=x-(ind<<Dint3);
273  // return ((delta*logexp_table(ind+1) + ((1<<Dint3)-delta)*logexp_table(ind)) >> Dint3);
274 
275  // Without interpolation
276  return logexp_table(ind);
277 }
278 
279 
281 {
282  QLLR x, maxab;
283 
284  if (a > b) {
285  maxab = a;
286  x = a - b;
287  }
288  else {
289  maxab = b;
290  x = b - a;
291  }
292 
293  if (maxab >= QLLR_MAX)
294  return QLLR_MAX;
295  else
296  return (maxab + logexp(x));
297 }
298 
299 }
300 
301 #endif
SourceForge Logo

Generated on Sat May 25 2013 16:32:21 for IT++ by Doxygen 1.8.2