22 #include "pybind11/pybind11.h"
23 #include "pybind11/stl.h"
24 #include "pybind11/numpy.h"
25 #include "ndarray/pybind11.h"
31 using namespace py::literals;
38 template <
typename PyClass>
39 void declareCommonIntervalInterface(
PyClass &
cls) {
41 using Element =
typename T::Element;
42 cls.def(py::init<>());
45 cls.def_static(
"fromSpannedPoints", [](ndarray::Array<Element const, 1>
const &elements) {
46 return T::fromSpannedPoints(elements);
48 cls.def_static(
"fromSpannedPoints",
52 if (kw.contains(
"min")) {
53 if (kw.contains(
"max")) {
54 return T::fromMinMax(py::cast<Element>(kw[
"min"]), py::cast<Element>(kw[
"max"]));
56 if (kw.contains(
"size")) {
57 return T::fromMinSize(py::cast<Element>(kw[
"min"]), py::cast<Element>(kw[
"size"]));
60 if (kw.contains(
"max") && kw.contains(
"size")) {
61 return T::fromMaxSize(py::cast<Element>(kw[
"max"]), py::cast<Element>(kw[
"size"]));
63 if (kw.contains(
"center") && kw.contains(
"size")) {
64 return T::fromCenterSize(py::cast<Element>(kw[
"center"]), py::cast<Element>(kw[
"size"]));
67 PyErr_SetString(PyExc_TypeError,
68 "General constructor requires exactly 2 of the following keyword-only "
69 "arguments: (min, max, center, size).");
70 throw py::error_already_set();
72 cls.def(py::init<T const &>());
73 cls.def(
"__eq__", [](T
const &
self, T
const &
other) {
return self ==
other; }, py::is_operator());
74 cls.def(
"__ne__", [](T
const &
self, T
const &
other) {
return self !=
other; }, py::is_operator());
75 cls.def(
"getMin", &T::getMin);
76 cls.def_property_readonly(
"min", &T::getMin);
77 cls.def(
"getMax", &T::getMax);
78 cls.def_property_readonly(
"max", &T::getMax);
81 cls.def(
"isEmpty", &T::isEmpty);
82 cls.def(
"contains", py::overload_cast<T const &>(&
T::contains, py::const_));
83 cls.def(
"contains", py::vectorize(
static_cast<bool (T::*)(Element)
const noexcept
>(&
T::contains)));
84 cls.def(
"__contains__", py::overload_cast<Element>(&
T::contains, py::const_));
85 cls.def(
"__contains__", py::overload_cast<T const &>(&
T::contains, py::const_));
86 cls.def(
"overlaps", &T::overlaps);
87 cls.def(
"intersects", &T::intersects);
88 cls.def(
"isDisjointFrom", &T::isDisjointFrom);
89 cls.def(
"dilatedBy", &T::dilatedBy);
90 cls.def(
"erodedBy", &T::erodedBy);
91 cls.def(
"shiftedBy", &T::shiftedBy);
92 cls.def(
"reflectedAbout", &T::reflectedAbout);
93 cls.def(
"expandedTo", py::overload_cast<Element>(&T::expandedTo, py::const_));
94 cls.def(
"expandedTo", py::overload_cast<T const &>(&T::expandedTo, py::const_));
95 cls.def(
"clippedTo", &T::clippedTo);
96 cls.def(
"__str__", &T::toString);
98 cls.def(
"__reduce__", [
cls](IntervalD
const &
self) {
99 return py::make_tuple(
cls,
make_tuple(py::cast(
self.getMin()), py::cast(
self.getMax())));
107 [](
auto &mod,
auto &
cls) {
108 py::enum_<IntervalI::EdgeHandlingEnum>(cls,
"EdgeHandlingEnum")
109 .value(
"EXPAND", IntervalI::EdgeHandlingEnum::EXPAND)
110 .value(
"SHRINK", IntervalI::EdgeHandlingEnum::SHRINK);
111 cls.def(py::init<IntervalD const &, IntervalI::EdgeHandlingEnum>(),
"other"_a,
112 "edgeHandling"_a = IntervalI::EdgeHandlingEnum::EXPAND);
113 cls.def(
"getBegin", &IntervalI::getBegin);
114 cls.def_property_readonly(
"begin", &IntervalI::getBegin);
115 cls.def(
"getEnd", &IntervalI::getEnd);
116 cls.def_property_readonly(
"end", &IntervalI::getEnd);
117 declareCommonIntervalInterface(cls);
121 [](
auto &mod,
auto &
cls) {
122 cls.def(py::init<IntervalI const &>());
123 cls.def(
"getCenter", &IntervalD::getCenter);
124 cls.def_property_readonly(
"center", &IntervalD::getCenter);
125 cls.def(
"isFinite", &IntervalD::isFinite);
126 declareCommonIntervalInterface(cls);