8#ifndef META_OCEAN_MATH_LOOKUP2_H
9#define META_OCEAN_MATH_LOOKUP2_H
28template <
typename T,
typename TScalar = Scalar>
51 inline const T*
data()
const;
93 explicit inline operator bool()
const;
196template <
typename T,
typename TScalar = Scalar>
252 inline bool isInside(
const TScalar x,
const TScalar y)
const;
259 inline size_t binX(
const TScalar x)
const;
266 inline size_t binY(
const TScalar y)
const;
422template <
typename T,
typename TScalar = Scalar>
530 bool bilinearValue(
const TScalar x,
const TScalar y,
const unsigned int minimalValidBins, T& value)
const;
634template <
typename T,
typename TScalar = Scalar>
690 inline bool isInside(
const TScalar x,
const TScalar y)
const;
697 inline size_t binX(
const TScalar x)
const;
704 inline size_t binY(
const TScalar y)
const;
765 template <
typename TTarget = T>
779 template <
typename TTarget = T>
780 void bilinearValues(
const size_t x,
const size_t y,
const size_t size, TTarget* values)
const;
792 template <
typename TTarget = T>
793 void bilinearValues(
const size_t y, TTarget* values,
const bool isOptimized)
const;
810 void bilinearValue(
const TScalar x,
const TScalar y, T& topLeft, T& topRight, T& bottomLeft, T& bottomRight, TScalar& factorTopLeft, TScalar& factorTopRight, TScalar& factorBottomLeft, TScalar& factorBottomRight)
const;
903template <
typename T,
typename TScalar>
918template <
typename T,
typename TScalar>
928 values_(std::move(lookup.values_))
935 lookup.invSizeX_ = 0;
936 lookup.invSizeY_ = 0;
937 lookup.invBinsX_ = 0;
938 lookup.invBinsY_ = 0;
941template <
typename T,
typename TScalar>
947template <
typename T,
typename TScalar>
953template <
typename T,
typename TScalar>
959template <
typename T,
typename TScalar>
965template <
typename T,
typename TScalar>
971template <
typename T,
typename TScalar>
977template <
typename T,
typename TScalar>
993template <
typename T,
typename TScalar>
1006 values_ = std::move(lookup.values_);
1012 lookup.invSizeX_ = 0;
1013 lookup.invSizeY_ = 0;
1014 lookup.invBinsX_ = 0;
1015 lookup.invBinsY_ = 0;
1021template <
typename T,
typename TScalar>
1027template <
typename T,
typename TScalar>
1033template <
typename T,
typename TScalar>
1039template <
typename T,
typename TScalar>
1042 return !(*
this == lookup);
1045template <
typename T,
typename TScalar>
1052template <
typename T,
typename TScalar>
1059template <
typename T,
typename TScalar>
1072 ocean_assert(
sizeX > 0);
1073 ocean_assert(
sizeY > 0);
1077 ocean_assert(
binsX > 0);
1078 ocean_assert(
binsY > 0);
1083template <
typename T,
typename TScalar>
1087 ocean_assert(binValues);
1098 ocean_assert(
sizeX > 0);
1099 ocean_assert(
sizeY > 0);
1103 ocean_assert(
binsX > 0);
1104 ocean_assert(
binsY > 0);
1108 for (
size_t n = 0; n < this->
values_.size(); ++n)
1110 this->
values_[n] = binValues[n];
1114template <
typename T,
typename TScalar>
1127 ocean_assert(
sizeX > 0);
1128 ocean_assert(
sizeY > 0);
1132 ocean_assert(this->
binsX_ > 0);
1133 ocean_assert(this->
binsY_ > 0);
1138template <
typename T,
typename TScalar>
1141 ocean_assert(!this->
isEmpty());
1142 return x >= TScalar(0) && y >= TScalar(0) && x <= TScalar(this->
sizeX_ - 1) && y <= TScalar(this->
sizeY_ - 1);
1145template <
typename T,
typename TScalar>
1148 ocean_assert(this->
sizeX_ > 0);
1149 ocean_assert(x >= 0 && x <= TScalar(this->
sizeX_ - 1));
1152 ocean_assert(result < this->
binsX_);
1157template <
typename T,
typename TScalar>
1160 ocean_assert(this->
sizeY_ > 0);
1161 ocean_assert(y >= 0 && y <= TScalar(this->
sizeY_ - 1));
1164 ocean_assert(result < this->
binsY_);
1169template <
typename T,
typename TScalar>
1172 ocean_assert(binX < this->
binsX_);
1175 ocean_assert(
binX == this->binX(TScalar(x)));
1180template <
typename T,
typename TScalar>
1183 ocean_assert(binY < this->
binsY_);
1186 ocean_assert(
binY == this->binY(TScalar(y)));
1191template <
typename T,
typename TScalar>
1194 ocean_assert(binX < this->
binsX_);
1198 ocean_assert(x >= 1);
1199 ocean_assert(
binX == this->binX(TScalar(x - 1)));
1204template <
typename T,
typename TScalar>
1207 ocean_assert(binY < this->
binsY_);
1211 ocean_assert(y >= 1);
1212 ocean_assert(
binY == this->binY(TScalar(y - 1)));
1217template <
typename T,
typename TScalar>
1220 ocean_assert(binX < this->
binsX_);
1223 ocean_assert(result >= 0 && result < TScalar(this->
sizeX_));
1228template <
typename T,
typename TScalar>
1231 ocean_assert(binY < this->
binsY_);
1234 ocean_assert(result >= 0 && result < TScalar(this->
sizeY_));
1239template <
typename T,
typename TScalar>
1247template <
typename T,
typename TScalar>
1250 ocean_assert(binX < this->
binsX_ && binY < this->
binsY_);
1254template <
typename T,
typename TScalar>
1257 ocean_assert(binX < this->
binsX_ && binY < this->
binsY_);
1261template <
typename T,
typename TScalar>
1264 ocean_assert(this->
isInside(x, y));
1266 const size_t bx = this->
binX(x);
1267 const size_t by = this->
binY(y);
1272template <
typename T,
typename TScalar>
1276 ocean_assert(this->
isInside(x, y));
1278 const size_t bX = this->
binX(x);
1279 const size_t bY = this->
binY(y);
1284 const size_t xLowBin = (x >= bCenterX) ? bX : max(0,
int(bX) - 1);
1285 const size_t xHighBin = (x < bCenterX) ? bX : min(xLowBin + 1, this->
binsX_ - 1);
1286 const size_t yLowBin = (y >= bCenterY) ? bY : max(0,
int(bY) - 1);
1287 const size_t yHighBin = (y < bCenterY) ? bY : min(yLowBin + 1, this->
binsY_ - 1);
1288 ocean_assert(((xLowBin == 0 || xLowBin == this->
binsX_ - 1) && xHighBin == xLowBin) || xLowBin + 1 == xHighBin);
1289 ocean_assert(((yLowBin == 0 || yLowBin == this->
binsY_ - 1) && yHighBin == yLowBin) || yLowBin + 1 == yHighBin);
1295 ocean_assert(leftCenter <= rightCenter);
1296 ocean_assert(topCenter <= bottomCenter);
1301 const TScalar xFactor = xLowBin != xHighBin ? (x - leftCenter) / (rightCenter - leftCenter) : TScalar(1);
1302 const TScalar yFactor = yLowBin != yHighBin ? (y - topCenter) / (bottomCenter - topCenter) : TScalar(1);
1307 const TScalar factorTopLeft = (TScalar(1) - xFactor) * (TScalar(1) - yFactor);
1308 const TScalar factorTopRight = xFactor * (TScalar(1) - yFactor);
1309 const TScalar factorBottomLeft = (TScalar(1) - xFactor) * yFactor;
1310 const TScalar factorBottomRight = xFactor * yFactor;
1317 return topLeft * factorTopLeft + topRight * factorTopRight
1318 + bottomLeft * factorBottomLeft + bottomRight * factorBottomRight;
1321template <
typename T,
typename TScalar>
1325 ocean_assert(this->
isInside(x, y));
1327 const size_t bX = this->
binX(x);
1328 const size_t bY = this->
binY(y);
1333 const size_t xLowBin = (x >= bCenterX) ? bX : max(0,
int(bX) - 1);
1334 const size_t xHighBin = (x < bCenterX) ? bX : min(xLowBin + 1, this->
binsX_ - 1);
1335 const size_t yLowBin = (y >= bCenterY) ? bY : max(0,
int(bY) - 1);
1336 const size_t yHighBin = (y < bCenterY) ? bY : min(yLowBin + 1, this->
binsY_ - 1);
1337 ocean_assert(((xLowBin == 0 || xLowBin == this->
binsX_ - 1) && xHighBin == xLowBin) || xLowBin + 1 == xHighBin);
1338 ocean_assert(((yLowBin == 0 || yLowBin == this->
binsY_ - 1) && yHighBin == yLowBin) || yLowBin + 1 == yHighBin);
1341 const size_t xMinusBin = max(0,
int(xLowBin) - 1);
1342 const size_t xPlusBin = min(xHighBin + 1, this->
binsX_ - 1);
1343 const size_t yMinusBin = max(0,
int(yLowBin) - 1);
1344 const size_t yPlusBin = min(yHighBin + 1, this->
binsY_ - 1);
1350 ocean_assert(leftCenter <= rightCenter);
1351 ocean_assert(topCenter <= bottomCenter);
1356 const TScalar xFactor = xLowBin != xHighBin ? (x - leftCenter) / (rightCenter - leftCenter) : TScalar(1);
1357 const TScalar yFactor = yLowBin != yHighBin ? (y - topCenter) / (bottomCenter - topCenter) : TScalar(1);
1368template <
typename T,
typename TScalar>
1376template <
typename T,
typename TScalar>
1384template <
typename T,
typename TScalar>
1392template <
typename T,
typename TScalar>
1395 ocean_assert(binX < this->
binsX_ && binY < this->
binsY_);
1399template <
typename T,
typename TScalar>
1406template <
typename T,
typename TScalar>
1414template <
typename T,
typename TScalar>
1422template <
typename T,
typename TScalar>
1430template <
typename T,
typename TScalar>
1438template <
typename T,
typename TScalar>
1446template <
typename T,
typename TScalar>
1454template <
typename T,
typename TScalar>
1457 ocean_assert(binX < this->
binsX_ && binY < this->
binsY_);
1461template <
typename T,
typename TScalar>
1466 ocean_assert(this->
isInside(x, y));
1468 const size_t bx = this->
binX(x);
1469 const size_t by = this->
binY(y);
1480template <
typename T,
typename TScalar>
1485 ocean_assert(this->
isInside(x, y));
1487 const size_t bX = this->
binX(x);
1488 const size_t bY = this->
binY(y);
1493 const size_t xLowBin = (x >= bCenterX) ? bX : max(0,
int(bX) - 1);
1494 const size_t xHighBin = (x < bCenterX) ? bX : min(xLowBin + 1, this->
binsX_ - 1);
1495 const size_t yLowBin = (y >= bCenterY) ? bY : max(0,
int(bY) - 1);
1496 const size_t yHighBin = (y < bCenterY) ? bY : min(yLowBin + 1, this->
binsY_ - 1);
1497 ocean_assert(((xLowBin == 0 || xLowBin == this->
binsX_ - 1) && xHighBin == xLowBin) || xLowBin + 1 == xHighBin);
1498 ocean_assert(((yLowBin == 0 || yLowBin == this->
binsY_ - 1) && yHighBin == yLowBin) || yLowBin + 1 == yHighBin);
1504 ocean_assert(leftCenter <= rightCenter);
1505 ocean_assert(topCenter <= bottomCenter);
1510 const TScalar xFactor = xLowBin != xHighBin ? (x - leftCenter) / (rightCenter - leftCenter) : TScalar(1);
1511 const TScalar yFactor = yLowBin != yHighBin ? (y - topCenter) / (bottomCenter - topCenter) : TScalar(1);
1521 const bool validTopLeft =
validBins_[yLowBin * this->
binsX_ + xLowBin] != 0u;
1522 const bool validTopRight =
validBins_[yLowBin * this->
binsX_ + xHighBin] != 0u;
1523 const bool validBottomLeft =
validBins_[yHighBin * this->
binsX_ + xLowBin] != 0u;
1524 const bool validBottomRight =
validBins_[yHighBin * this->
binsX_ + xHighBin] != 0u;
1526 if (validTopLeft || validTopRight || validBottomLeft || validBottomRight)
1528 value =
Interpolation::bilinear(topLeft, topRight, bottomLeft, bottomRight, validTopLeft, validTopRight, validBottomLeft, validBottomRight, xFactor, yFactor);
1535template <
typename T,
typename TScalar>
1538 ocean_assert(minimalValidBins >= 1u && minimalValidBins <= 4u);
1541 ocean_assert(this->
isInside(x, y));
1543 const size_t bX = this->
binX(x);
1544 const size_t bY = this->
binY(y);
1549 const size_t xLowBin = (x >= bCenterX) ? bX : max(0,
int(bX) - 1);
1550 const size_t xHighBin = (x < bCenterX) ? bX : min(xLowBin + 1, this->
binsX_ - 1);
1551 const size_t yLowBin = (y >= bCenterY) ? bY : max(0,
int(bY) - 1);
1552 const size_t yHighBin = (y < bCenterY) ? bY : min(yLowBin + 1, this->
binsY_ - 1);
1553 ocean_assert(((xLowBin == 0 || xLowBin == this->
binsX_ - 1) && xHighBin == xLowBin) || xLowBin + 1 == xHighBin);
1554 ocean_assert(((yLowBin == 0 || yLowBin == this->
binsY_ - 1) && yHighBin == yLowBin) || yLowBin + 1 == yHighBin);
1560 ocean_assert(leftCenter <= rightCenter);
1561 ocean_assert(topCenter <= bottomCenter);
1566 const TScalar xFactor = xLowBin != xHighBin ? (x - leftCenter) / (rightCenter - leftCenter) : TScalar(1);
1567 const TScalar yFactor = yLowBin != yHighBin ? (y - topCenter) / (bottomCenter - topCenter) : TScalar(1);
1577 const bool validTopLeft =
validBins_[yLowBin * this->
binsX_ + xLowBin] != 0u;
1578 const bool validTopRight =
validBins_[yLowBin * this->
binsX_ + xHighBin] != 0u;
1579 const bool validBottomLeft =
validBins_[yHighBin * this->
binsX_ + xLowBin] != 0u;
1580 const bool validBottomRight =
validBins_[yHighBin * this->
binsX_ + xHighBin] != 0u;
1582 ocean_assert(validTopLeft == 0 || validTopLeft == 1);
1583 ocean_assert(validTopRight == 0 || validTopRight == 1);
1584 ocean_assert(validBottomLeft == 0 || validBottomLeft == 1);
1585 ocean_assert(validBottomRight == 0 || validBottomRight == 1);
1587 if ((
unsigned int)(validTopLeft + validTopRight + validBottomLeft + validBottomRight) >= minimalValidBins)
1589 value =
Interpolation::bilinear(topLeft, topRight, bottomLeft, bottomRight, validTopLeft, validTopRight, validBottomLeft, validBottomRight, xFactor, yFactor);
1596template <
typename T,
typename TScalar>
1604template <
typename T,
typename TScalar>
1612template <
typename T,
typename TScalar>
1615 ocean_assert(binX < this->
binsX_ && binY < this->
binsY_);
1621template <
typename T,
typename TScalar>
1624 ocean_assert(binX < this->
binsX_ && binY < this->
binsY_);
1628template <
typename T,
typename TScalar>
1631 if (
this != &lookup)
1640template <
typename T,
typename TScalar>
1646template <
typename T,
typename TScalar>
1649 return !(*
this == lookup);
1652template <
typename T,
typename TScalar>
1654 Lookup2<T, TScalar>(std::move(lookup))
1659template <
typename T,
typename TScalar>
1666template <
typename T,
typename TScalar>
1679 ocean_assert(
sizeX >= 1);
1680 ocean_assert(
sizeY >= 1);
1684 ocean_assert(
binsX > 0);
1685 ocean_assert(
binsY > 0);
1690template <
typename T,
typename TScalar>
1694 ocean_assert(binCornerValues);
1705 ocean_assert(
sizeX > 1);
1706 ocean_assert(
sizeY > 1);
1710 ocean_assert(
binsX > 0);
1711 ocean_assert(
binsY > 0);
1715 for (
size_t n = 0; n < this->
values_.size(); ++n)
1717 this->
values_[n] = binCornerValues[n];
1721template <
typename T,
typename TScalar>
1734 ocean_assert(
sizeX > 1);
1735 ocean_assert(
sizeY > 1);
1739 ocean_assert(this->
binsX_ > 0);
1740 ocean_assert(this->
binsY_ > 0);
1745template <
typename T,
typename TScalar>
1748 ocean_assert(!this->
isEmpty());
1749 return x >= TScalar(0) && y >= TScalar(0) && x <= TScalar(this->
sizeX_) && y <= TScalar(this->
sizeY_);
1752template <
typename T,
typename TScalar>
1755 ocean_assert(this->
sizeX_ > 0);
1756 ocean_assert(x >= 0 && x <= TScalar(this->
sizeX_));
1759 ocean_assert(result <= this->
binsX_);
1764template <
typename T,
typename TScalar>
1767 ocean_assert(this->
sizeY_ > 0);
1768 ocean_assert(y >= 0 && y <= TScalar(this->
sizeY_));
1771 ocean_assert(result <= this->
binsY_);
1776template <
typename T,
typename TScalar>
1779 ocean_assert(binX <= this->
binsX_ && this->
sizeX_ >= 1);
1787template <
typename T,
typename TScalar>
1790 ocean_assert(binY <= this->
binsY_ && this->
sizeY_ >= 1);
1798template <
typename T,
typename TScalar>
1806template <
typename T,
typename TScalar>
1809 ocean_assert(binX <= this->
binsX_ && binY <= this->
binsY_);
1813template <
typename T,
typename TScalar>
1816 ocean_assert(this->
isInside(x, y));
1819 ocean_assert(bx <= this->
binsX_);
1822 ocean_assert(by <= this->
binsY_);
1824 return this->
values_[by * (this->binsX_ + 1) + bx];
1827template <
typename T,
typename TScalar>
1831 ocean_assert(this->
isInside(x, y));
1833 const size_t xLowBin = this->
binX(x);
1834 const size_t yLowBin = this->
binY(y);
1836 ocean_assert(xLowBin <= this->
binsX_);
1837 ocean_assert(yLowBin <= this->
binsY_);
1842 const TScalar xFactor = (x - leftPosition) * TScalar(this->binsX_) * this->
invSizeX_;
1843 const TScalar yFactor = (y - topPosition) * TScalar(this->binsY_) * this->
invSizeY_;
1846 if (std::is_same<TScalar, float>::value)
1858 const TScalar factorTopLeft = (TScalar(1) - xFactor) * (TScalar(1) - yFactor);
1859 const TScalar factorTopRight = xFactor * (TScalar(1) - yFactor);
1860 const TScalar factorBottomLeft = (TScalar(1) - xFactor) * yFactor;
1861 const TScalar factorBottomRight = xFactor * yFactor;
1863 const size_t xHighBin = min(xLowBin + 1, this->binsX_);
1864 const size_t yHighBin = min(yLowBin + 1, this->binsY_);
1871 return topLeft * factorTopLeft + topRight * factorTopRight
1872 + bottomLeft * factorBottomLeft + bottomRight * factorBottomRight;
1875template <
typename T,
typename TScalar>
1876template <
typename TTarget>
1880 ocean_assert(this->binsX_ <= this->
sizeX_ && this->binsY_ <= this->
sizeY_);
1882 ocean_assert(y < this->
sizeY_);
1883 ocean_assert(values !=
nullptr);
1885 const size_t yLowBin = (y * this->
binsY_) / this->sizeY_;
1886 ocean_assert(yLowBin < this->
binsY_);
1887 ocean_assert(std::abs(
int(yLowBin) -
int(this->
binY(TScalar(y)))) <= 1);
1889 const size_t yHighBin = yLowBin + 1;
1890 ocean_assert(yHighBin <= this->
binsY_);
1894 ocean_assert(yLowBinPosition < yHighBinPosition);
1896 const TScalar yFactor = (TScalar(y) - yLowBinPosition) / (yHighBinPosition - yLowBinPosition);
1902 Vector2 leftBinValue = *lowBinValues++ * (TScalar(1) - yFactor) + *highBinValues++ * yFactor;
1903 Vector2 rightBinValue = *lowBinValues++ * (TScalar(1) - yFactor) + *highBinValues++ * yFactor;
1905 unsigned int nextBinX = 1u;
1907 TScalar leftBinPositionX = TScalar(0);
1908 TScalar rightBinPositionX = TScalar(nextBinX++ * this->
sizeX_) * this->
invBinsX_;
1911 TScalar invBinWidthX = TScalar(1) / (rightBinPositionX - leftBinPositionX);
1913 for (
size_t x = 0; x < this->
sizeX_; ++x)
1915 if (TScalar(x) > rightBinPositionX)
1917 leftBinValue = rightBinValue;
1918 rightBinValue = *lowBinValues++ * (TScalar(1) - yFactor) + *highBinValues++ * yFactor;
1920 leftBinPositionX = rightBinPositionX;
1921 rightBinPositionX = TScalar(nextBinX++ * this->sizeX_) * this->
invBinsX_;
1924 invBinWidthX = TScalar(1) / (rightBinPositionX - leftBinPositionX);
1927 ocean_assert(leftBinPositionX <= TScalar(x));
1929 const TScalar xFactor = (TScalar(x) - leftBinPositionX) * invBinWidthX;
1931 if constexpr (std::is_same<TScalar, float>::value)
1940 values[x] = TTarget(leftBinValue * (TScalar(1) - xFactor) + rightBinValue * xFactor);
1943 const T debugTestValue = this->
bilinearValue(TScalar(x), TScalar(y));
1944 const TScalar debugError = debugTestValue.distance(T(values[x]));
1945 ocean_assert(debugError < TScalar(0.1));
1950template <
typename T,
typename TScalar>
1951template <
typename TTarget>
1955 ocean_assert(this->binsX_ <= this->
sizeX_ && this->binsY_ <= this->
sizeY_);
1957 ocean_assert(x + size <= this->
sizeX_);
1959 ocean_assert(y < this->
sizeY_);
1960 ocean_assert(values !=
nullptr);
1962 ocean_assert(size >= 1);
1964 const size_t xLowBin = (x * this->
binsX_) / this->sizeX_;
1965 ocean_assert(xLowBin < this->
binsX_);
1966 ocean_assert(std::abs(
int(xLowBin) -
int(this->
binX(TScalar(x)))) <= 1);
1968 const size_t yLowBin = (y * this->
binsY_) / this->sizeY_;
1969 ocean_assert(yLowBin < this->
binsY_);
1970 ocean_assert(std::abs(
int(yLowBin) -
int(this->
binY(TScalar(y)))) <= 1);
1972 const size_t yHighBin = yLowBin + 1;
1973 ocean_assert(yHighBin <= this->
binsY_);
1977 ocean_assert(yLowBinPosition < yHighBinPosition);
1979 const TScalar yFactor = (TScalar(y) - yLowBinPosition) / (yHighBinPosition - yLowBinPosition);
1982 const Vector2* lowBinValues = this->
values_.data() + (yLowBin * (this->binsX_ + 1)) + xLowBin;
1983 const Vector2* highBinValues = this->
values_.data() + (yHighBin * (this->binsX_ + 1)) + xLowBin;
1985 Vector2 leftBinValue = *lowBinValues++ * (TScalar(1) - yFactor) + *highBinValues++ * yFactor;
1986 Vector2 rightBinValue = *lowBinValues++ * (TScalar(1) - yFactor) + *highBinValues++ * yFactor;
1988 size_t nextBinX = xLowBin + 1u;
1990 TScalar leftBinPositionX = TScalar(xLowBin * this->sizeX_) * this->
invBinsX_;
1991 TScalar rightBinPositionX = TScalar(nextBinX++ * this->sizeX_) * this->
invBinsX_;
1994 TScalar invBinWidthX = TScalar(1) / (rightBinPositionX - leftBinPositionX);
1996 for (
size_t nX = x; nX < x + size; ++nX)
1998 if (TScalar(nX) > rightBinPositionX)
2000 leftBinValue = rightBinValue;
2001 rightBinValue = *lowBinValues++ * (TScalar(1) - yFactor) + *highBinValues++ * yFactor;
2003 leftBinPositionX = rightBinPositionX;
2004 rightBinPositionX = TScalar(nextBinX++ * this->sizeX_) * this->
invBinsX_;
2007 invBinWidthX = TScalar(1) / (rightBinPositionX - leftBinPositionX);
2012 const TScalar xFactor = (TScalar(nX) - leftBinPositionX) * invBinWidthX;
2015 *values++ = TTarget(leftBinValue * (TScalar(1) - xFactor) + rightBinValue * xFactor);
2018 const T debugTestValue = this->
bilinearValue(TScalar(nX), TScalar(y));
2019 const TScalar debugError = debugTestValue.distance(T(TTarget(leftBinValue * (TScalar(1) - xFactor) + rightBinValue * xFactor)));
2020 ocean_assert(debugError < TScalar(0.1));
2025template <
typename T,
typename TScalar>
2026template <
typename TTarget>
2036 ocean_assert(this->binsX_ <= this->
sizeX_ && this->binsY_ <= this->
sizeY_);
2037 ocean_assert(y < this->
sizeY_);
2038 ocean_assert(values !=
nullptr);
2040 const size_t yLowBin = (y * this->
binsY_) / this->sizeY_;
2041 ocean_assert(yLowBin < this->
binsY_);
2043 const size_t yHighBin = yLowBin + 1;
2044 ocean_assert(yHighBin <= this->
binsY_);
2048 ocean_assert(yLowBinPosition < yHighBinPosition);
2050 const TScalar yFactor = (TScalar(y) - yLowBinPosition) / (yHighBinPosition - yLowBinPosition);
2059 for (
size_t bin = 0; bin < this->
binsX_; ++bin)
2061 const Vector2 leftBinValue = lowBinValues[bin] * (TScalar(1) - yFactor) + highBinValues[bin] * yFactor;
2062 const Vector2 rightBinValue = lowBinValues[bin + 1] * (TScalar(1) - yFactor) + highBinValues[bin + 1] * yFactor;
2064 const TScalar leftBinPositionX = TScalar(bin * this->
sizeX_) * this->
invBinsX_;
2065 const TScalar rightBinPositionX = TScalar((bin + 1) * this->sizeX_) * this->
invBinsX_;
2068 const TScalar invBinWidthX = TScalar(1) / (rightBinPositionX - leftBinPositionX);
2070 const Vector2 delta = (rightBinValue - leftBinValue) * invBinWidthX;
2074 const size_t xEnd = (bin + 1 < this->binsX_)
2075 ? std::min(
static_cast<size_t>(rightBinPositionX) + 1, this->sizeX_)
2079 const TScalar xStartFactor = (TScalar(xStart) - leftBinPositionX) * invBinWidthX;
2080 const Vector2 startValue = leftBinValue + (rightBinValue - leftBinValue) * xStartFactor;
2082 TScalar currentX = startValue.
x();
2083 TScalar currentY = startValue.
y();
2084 const TScalar deltaX = delta.
x();
2085 const TScalar deltaY = delta.
y();
2087 for (
size_t x = xStart; x < xEnd; ++x)
2089 values[x] = TTarget(currentX, currentY);
2099template <
typename T,
typename TScalar>
2100void LookupCorner2<T, TScalar>::bilinearValue(
const TScalar x,
const TScalar y, T& topLeft, T& topRight, T& bottomLeft, T& bottomRight, TScalar& factorTopLeft, TScalar& factorTopRight, TScalar& factorBottomLeft, TScalar& factorBottomRight)
const
2103 ocean_assert(this->
isInside(x, y));
2105 const size_t xLowBin = this->
binX(x);
2106 const size_t yLowBin = this->
binY(y);
2108 ocean_assert(xLowBin <= this->
binsX_);
2109 ocean_assert(yLowBin <= this->
binsY_);
2114 const TScalar xFactor = (x - leftPosition) * TScalar(this->binsX_) * this->
invSizeX_;
2115 const TScalar yFactor = (y - topPosition) * TScalar(this->binsY_) * this->
invSizeY_;
2118 if (std::is_same<TScalar, float>::value)
2130 factorTopLeft = (TScalar(1) - xFactor) * (TScalar(1) - yFactor);
2131 factorTopRight = xFactor * (TScalar(1) - yFactor);
2132 factorBottomLeft = (TScalar(1) - xFactor) * yFactor;
2133 factorBottomRight = xFactor * yFactor;
2135 const size_t xHighBin = min(xLowBin + 1, this->binsX_);
2136 const size_t yHighBin = min(yLowBin + 1, this->binsY_);
2144template <
typename T,
typename TScalar>
2148 ocean_assert(this->
isInside(x, y));
2150 const size_t xLowBin = this->
binX(x);
2151 const size_t yLowBin = this->
binY(y);
2153 ocean_assert(xLowBin <= this->
binsX_);
2154 ocean_assert(yLowBin <= this->
binsY_);
2159 const TScalar xFactor = (x - leftPosition) * TScalar(this->binsX_) * this->
invSizeX_;
2160 const TScalar yFactor = (y - topPosition) * TScalar(this->binsY_) * this->
invSizeY_;
2163 if (std::is_same<TScalar, float>::value)
2175 const size_t xHighBin = min(xLowBin + 1, this->binsX_);
2176 const size_t yHighBin = min(yLowBin + 1, this->binsY_);
2179 const size_t xMinusBin = max(0,
int(xLowBin) - 1);
2180 const size_t xPlusBin = min(xLowBin + 2, this->binsX_);
2181 const size_t yMinusBin = max(0,
int(yLowBin) - 1);
2182 const size_t yPlusBin = min(yLowBin + 2, this->binsY_);
2190template <
typename T,
typename TScalar>
2198template <
typename T,
typename TScalar>
2206template <
typename T,
typename TScalar>
2214template <
typename T,
typename TScalar>
2217 ocean_assert(binX <= this->
binsX_ && binY <= this->
binsY_);
2221template <
typename T,
typename TScalar>
2226 for (
size_t n = 0; n < result.
values_.size(); ++n)
2234template <
typename T,
typename TScalar>
2237 for (
size_t n = 0; n < this->
values_.size(); ++n)
2245template <
typename T,
typename TScalar>
2250 for (
size_t n = 0; n < result.
values_.size(); ++n)
2258template <
typename T,
typename TScalar>
2261 for (
size_t n = 0; n < this->
values_.size(); ++n)
2269template <
typename T,
typename TScalar>
2276template <
typename T,
typename TScalar>
AdvancedLookupCenter2(const size_t sizeX, const size_t sizeY, const size_t binsX, const size_t binsY)
Creates a new lookup object by definition of the dimensions and bin numbers.
Definition Lookup2.h:1423
std::vector< unsigned char > ValidBins
Definition Lookup2.h:430
void setBinCenterValid(const size_t binX, const size_t binY, const bool isValid)
Sets whether a specific lookup bin is valid.
Definition Lookup2.h:1622
AdvancedLookupCenter2(AdvancedLookupCenter2< T, TScalar > &&lookup) noexcept
Move constructor.
Definition Lookup2.h:1415
bool nearestValue(const TScalar x, const TScalar y, T &value) const
Applies a lookup for a specific position in this lookup object.
Definition Lookup2.h:1462
bool bilinearValue(const TScalar x, const TScalar y, T &value) const
Applies a lookup for a specific position in this lookup object.
Definition Lookup2.h:1481
AdvancedLookupCenter2(const size_t sizeX, const size_t sizeY, const size_t binsX, const size_t binsY, const bool binsValid)
Creates a new lookup object by definition of the dimensions and bin numbers.
Definition Lookup2.h:1431
ValidBins validBins_
Definition Lookup2.h:595
bool clampedBilinearValue(const TScalar x, const TScalar y, T &value) const
Applies a lookup for a specific position in this lookup object while the position is clamped to match...
Definition Lookup2.h:1605
AdvancedLookupCenter2(const AdvancedLookupCenter2< T, TScalar > &lookup)
Copy constructor.
Definition Lookup2.h:1407
AdvancedLookupCenter2(const size_t sizeX, const size_t sizeY, const size_t binsX, const size_t binsY, const T *binValues, const unsigned char *validBins)
Creates a new lookup object by definition of the dimensions and bin numbers.
Definition Lookup2.h:1439
bool operator!=(const AdvancedLookupCenter2< T, TScalar > &lookup) const
Returns whether two lookup objects are not identical.
Definition Lookup2.h:1647
AdvancedLookupCenter2()=default
Creates a new empty lookup object.
void setBinCenterValue(const size_t binX, const size_t binY, const T &value, const bool isValid)
Sets the value of one specific lookup bin's center and defines whether this bin is valid.
Definition Lookup2.h:1613
bool clampedNearestValue(const TScalar x, const TScalar y, T &value) const
Applies a lookup for a specific position in this lookup object while the position is clamped to match...
Definition Lookup2.h:1597
bool operator==(const AdvancedLookupCenter2< T, TScalar > &lookup) const
Returns whether two lookup objects are identical.
Definition Lookup2.h:1641
bool binCenterValid(const size_t binX, const size_t binY) const
Returns whether a specific bin of this lookup object is valid.
Definition Lookup2.h:1455
AdvancedLookupCenter2(const size_t sizeX, const size_t sizeY, const AdvancedLookupCenter2< T, TScalar > &lookup)
Creates a new lookup object by definition of the dimensions and a given lookup object.
Definition Lookup2.h:1447
bool bilinearValue(const TScalar x, const TScalar y, const unsigned int minimalValidBins, T &value) const
Applies a lookup for a specific position in this lookup object.
Definition Lookup2.h:1536
AdvancedLookupCenter2< T, TScalar > & operator=(AdvancedLookupCenter2< T, TScalar > &&lookup) noexcept
Move operator.
Definition Lookup2.h:1629
static T cubic(const T &v0, const T &v1, const T &v2, const T &v3, const TFactor &t)
Performs a cubic (Catmull-Rom) interpolation between mainly two values while two further supporting p...
Definition Interpolation.h:644
static T bilinear(const T &v00, const T &v01, const T &v10, const T &v11, const TFactor &tx, const TFactor &ty)
Performs a bi-linear interpolation between four values within a 2x2 neighborhood.
Definition Interpolation.h:539
std::vector< T > Values
Definition of a vector holding lookup values.
Definition Lookup2.h:43
Values values_
The values of the lookup bins.
Definition Lookup2.h:169
Lookup2< T, TScalar > & operator=(const Lookup2< T, TScalar > &lookup)
Assign operator.
Definition Lookup2.h:978
TScalar invBinsY_
Inverse number of vertical bins.
Definition Lookup2.h:166
size_t binsY_
Number of vertical bins.
Definition Lookup2.h:154
size_t sizeY() const
Returns the vertical dimension of this lookup object.
Definition Lookup2.h:960
const T * data() const
Returns a pointer to the constant bin data (row aligned).
Definition Lookup2.h:942
TScalar invSizeY_
Inverse vertical dimension of this lookup object.
Definition Lookup2.h:160
size_t binsX_
Number of horizontal bins.
Definition Lookup2.h:151
size_t sizeX_
Horizontal dimension of this lookup object.
Definition Lookup2.h:145
size_t sizeX() const
Returns the horizontal dimension of this lookup object.
Definition Lookup2.h:954
bool operator==(const Lookup2< T, TScalar > &lookup) const
Returns whether two lookup objects are identical.
Definition Lookup2.h:1034
bool isEmpty() const
Returns whether this lookup object does not hold any lookup bin.
Definition Lookup2.h:1022
T Type
Definition of the lookup data type.
Definition Lookup2.h:36
size_t binsY() const
Returns the number of vertical bins of this lookup object.
Definition Lookup2.h:972
size_t sizeY_
Vertical dimension of this lookup object.
Definition Lookup2.h:148
TScalar invBinsX_
Inverse number of horizontal bins.
Definition Lookup2.h:163
size_t binsX() const
Returns the number of horizontal bins of this lookup object.
Definition Lookup2.h:966
bool operator!=(const Lookup2< T, TScalar > &lookup) const
Returns whether two lookup objects are not identical.
Definition Lookup2.h:1040
TScalar invSizeX_
Inverse horizontal dimension of this lookup object.
Definition Lookup2.h:157
Lookup2()=default
Creates a new empty lookup object.
T nearestValue(const TScalar x, const TScalar y) const
Applies a lookup for a specific position in this lookup object.
Definition Lookup2.h:1262
LookupCenter2< T, TScalar > & operator=(LookupCenter2< T, TScalar > &&lookup) noexcept
Move operator.
Definition Lookup2.h:1400
void setBinCenterValue(const size_t binX, const size_t binY, const T &value)
Sets the value of one specific lookup bin's center.
Definition Lookup2.h:1393
TScalar binCenterPositionY(const size_t binY) const
Returns the vertical center position of a specific bin in relation to the dimension of this lookup ob...
Definition Lookup2.h:1229
T clampedBilinearValue(const TScalar x, const TScalar y) const
Applies a lookup for a specific position in this lookup object while the position is clamped to match...
Definition Lookup2.h:1377
T clampedNearestValue(const TScalar x, const TScalar y) const
Applies a lookup for a specific position in this lookup object while the position is clamped to match...
Definition Lookup2.h:1369
T bicubicValue(const TScalar x, const TScalar y) const
Applies a lookup for a specific position in this lookup object.
Definition Lookup2.h:1322
LookupCenter2(const size_t sizeX, const size_t sizeY, const size_t binsX, const size_t binsY)
Creates a new lookup object by definition of the dimensions and bin numbers.
Definition Lookup2.h:1060
size_t binY(const TScalar y) const
Returns the vertical bin that corresponds to a precise vertical lookup position.
Definition Lookup2.h:1158
size_t binTopLeftY(const size_t binY) const
Returns the vertical top left position of a specified bin with pixel accuracy.
Definition Lookup2.h:1181
T clampedBicubicValue(const TScalar x, const TScalar y) const
Applies a lookup for a specific position in this lookup object while the position is clamped to match...
Definition Lookup2.h:1385
LookupCenter2(const LookupCenter2< T, TScalar > &lookup)
Copy constructor.
Definition Lookup2.h:1046
size_t binBottomRightY(const size_t binY) const
Returns the vertical bottom right position of a specified bin with pixel accuracy.
Definition Lookup2.h:1205
LookupCenter2()=default
Creates a new empty lookup object.
LookupCenter2(LookupCenter2< T, TScalar > &&lookup) noexcept
Move constructor.
Definition Lookup2.h:1053
TScalar binCenterPositionX(const size_t binX) const
Returns the horizontal center position of a specific bin in relation to the dimension of this lookup ...
Definition Lookup2.h:1218
size_t binBottomRightX(const size_t binX) const
Returns the horizontal bottom right position (including) of a specified bin with pixel accuracy.
Definition Lookup2.h:1192
size_t binTopLeftX(const size_t binX) const
Returns the horizontal top left position of a specified bin with pixel accuracy.
Definition Lookup2.h:1170
LookupCenter2(const size_t sizeX, const size_t sizeY, const LookupCenter2< T, TScalar > &lookup)
Creates a new lookup object by definition of the dimensions and a given lookup object.
Definition Lookup2.h:1115
Vector2 binCenterPosition(const size_t binX, const size_t binY) const
Returns the center position of a specific bin in relation to the dimension of this lookup object.
Definition Lookup2.h:1240
size_t binX(const TScalar x) const
Returns the horizontal bin that corresponds to a precise horizontal lookup position.
Definition Lookup2.h:1146
const T & binCenterValue(const size_t binX, const size_t binY) const
Returns the lookup value of a specific bin's center of this lookup object.
Definition Lookup2.h:1248
T bilinearValue(const TScalar x, const TScalar y) const
Applies a lookup for a specific position in this lookup object.
Definition Lookup2.h:1273
bool isInside(const TScalar x, const TScalar y) const
Returns whether a given position lies inside this lookup object and therefore whether this position c...
Definition Lookup2.h:1139
LookupCenter2(const size_t sizeX, const size_t sizeY, const size_t binsX, const size_t binsY, const T *binValues)
Creates a new lookup object by definition of the dimensions and bin numbers.
Definition Lookup2.h:1084
T & binCenterValue(const size_t binX, const size_t binY)
Returns the lookup value of a specific bin's center of this lookup object.
Definition Lookup2.h:1255
LookupCorner2(LookupCorner2< T, TScalar > &&lookup) noexcept
Move constructor.
Definition Lookup2.h:1660
T clampedNearestValue(const TScalar x, const TScalar y) const
Applies a lookup for a specific position in this lookup object while the position is clamped to match...
Definition Lookup2.h:2191
LookupCorner2()=default
Creates a new empty lookup object.
T clampedBicubicValue(const TScalar x, const TScalar y) const
Applies a lookup for a specific position in this lookup object while the position is clamped to match...
Definition Lookup2.h:2207
LookupCorner2< T, TScalar > & operator+=(const T &offset)
Adds an offset value to each lookup value.
Definition Lookup2.h:2235
bool isInside(const TScalar x, const TScalar y) const
Returns whether a given position lies inside this lookup object and therefore whether this position c...
Definition Lookup2.h:1746
LookupCorner2< T, TScalar > operator+(const T &offset) const
Adds an offset value to each lookup value.
Definition Lookup2.h:2222
Vector2 binTopLeftCornerPosition(const size_t binX, const size_t binY) const
Returns the corner position (the top left corner) of a specific bin in relation to the dimension of t...
Definition Lookup2.h:1799
const T & binTopLeftCornerValue(const size_t binX, const size_t binY) const
Returns the lookup value of a specific bin corner (the top left corner value) of this lookup object.
Definition Lookup2.h:1807
size_t binX(const TScalar x) const
Returns the horizontal bin that corresponds to a precise horizontal lookup position.
Definition Lookup2.h:1753
void bilinearValue(const TScalar x, const TScalar y, T &topLeft, T &topRight, T &bottomLeft, T &bottomRight, TScalar &factorTopLeft, TScalar &factorTopRight, TScalar &factorBottomLeft, TScalar &factorBottomRight) const
Applies a lookup for a specific position in this lookup object but does not apply the bilinear interp...
Definition Lookup2.h:2100
LookupCorner2(const size_t sizeX, const size_t sizeY, const LookupCorner2< T, TScalar > &lookup)
Creates a new lookup object by definition of the dimensions and a given lookup object.
Definition Lookup2.h:1722
void setBinTopLeftCornerValue(const size_t binX, const size_t binY, const T &value)
Sets the value of one specific lookup bin's top left corner.
Definition Lookup2.h:2215
LookupCorner2< T, TScalar > & operator-=(const T &offset)
Subtracts an offset value from each lookup value.
Definition Lookup2.h:2259
void bilinearValues(const size_t y, TTarget *values) const
Applies a lookup for an entire row in this lookup object.
Definition Lookup2.h:1877
void bilinearValues(const size_t y, TTarget *values, const bool isOptimized) const
Applies a lookup for an entire row in this lookup object, with an option to use an optimized accumula...
Definition Lookup2.h:2027
T nearestValue(const TScalar x, const TScalar y) const
Applies a lookup for a specific position in this lookup object.
Definition Lookup2.h:1814
T clampedBilinearValue(const TScalar x, const TScalar y) const
Applies a lookup for a specific position in this lookup object while the position is clamped to match...
Definition Lookup2.h:2199
T bicubicValue(const TScalar x, const TScalar y) const
Applies a lookup for a specific position in this lookup object.
Definition Lookup2.h:2145
size_t binY(const TScalar y) const
Returns the vertical bin that corresponds to a precise vertical lookup position.
Definition Lookup2.h:1765
void bilinearValues(const size_t x, const size_t y, const size_t size, TTarget *values) const
Applies a lookup for a subset of a row in this lookup object.
Definition Lookup2.h:1952
T bilinearValue(const TScalar x, const TScalar y) const
Applies a lookup for a specific position in this lookup object.
Definition Lookup2.h:1828
LookupCorner2(const LookupCorner2< T, TScalar > &lookup)
Copy constructor.
Definition Lookup2.h:1653
LookupCorner2(const size_t sizeX, const size_t sizeY, const size_t binsX, const size_t binsY, const T *binCornerValues)
Creates a new lookup object by definition of the dimensions and bin numbers.
Definition Lookup2.h:1691
LookupCorner2< T, TScalar > operator-(const T &offset) const
Subtracts an offset value from each lookup value.
Definition Lookup2.h:2246
TScalar binTopLeftCornerPositionY(const size_t binY) const
Returns the vertical corner position of a specific bin corner (the top left corner) in relation to th...
Definition Lookup2.h:1788
LookupCorner2(const size_t sizeX, const size_t sizeY, const size_t binsX, const size_t binsY)
Creates a new lookup object by definition of the dimensions and bin numbers.
Definition Lookup2.h:1667
TScalar binTopLeftCornerPositionX(const size_t binX) const
Returns the horizontal corner position of a specific bin corner (the top left corner) in relation to ...
Definition Lookup2.h:1777
LookupCorner2< T, TScalar > & operator=(LookupCorner2< T, TScalar > &&lookup) noexcept
Move operator.
Definition Lookup2.h:2277
LookupCorner2< T, TScalar > & operator=(const LookupCorner2< T, TScalar > &lookup)
Copy operator.
Definition Lookup2.h:2270
static constexpr T weakEps()
Returns a weak epsilon.
static constexpr bool isInsideRange(const T lower, const T value, const T upper, const T epsilon=NumericT< T >::eps())
Returns whether a value lies between a given range up to a provided epsilon border.
Definition Numeric.h:2881
static constexpr T eps()
Returns a small epsilon.
static T ceil(const T value)
Returns the smallest integer value that is not less than the given value.
Definition Numeric.h:1997
static constexpr bool isInsideWeakRange(const T lower, const T value, const T upper)
Returns whether a value lies between a given range up to a weak epsilon border.
Definition Numeric.h:2890
static bool isNotEqual(const T first, const T second)
Returns whether two values are not equal up to a small epsilon.
Definition Numeric.h:2622
const T & x() const noexcept
Returns the x value.
Definition Vector2.h:703
const T & y() const noexcept
Returns the y value.
Definition Vector2.h:715
T minmax(const T &lowerBoundary, const T &value, const T &upperBoundary)
This function fits a given parameter into a specified value range.
Definition base/Utilities.h:973
VectorT2< Scalar > Vector2
Definition of a 2D vector.
Definition Vector2.h:28
The namespace covering the entire Ocean framework.
Definition Accessor.h:15