PLaSK library

Loading...
Searching...
No Matches
change_space_size.hpp
Go to the documentation of this file.
1/*
2 * This file is part of PLaSK (https://plask.app) by Photonics Group at TUL
3 * Copyright (c) 2022 Lodz University of Technology
4 *
5 * This program is free software: you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation, version 3.
8 *
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
13 */
14#ifndef PLASK__FILTER__CHANGE_SPACE_SIZE_H
15#define PLASK__FILTER__CHANGE_SPACE_SIZE_H
16
17#include "base.hpp"
18#include "../mesh/basic.hpp"
19#include "../mesh/transformed.hpp"
20#include "../utils/warnings.hpp"
21
22 namespace plask {
23
25 template <typename PropertyT, PropertyType propertyType, typename VariadicTemplateTypesHolder>
26 struct DataFrom3Dto2DSourceImpl {
27 static_assert(propertyType == FIELD_PROPERTY || propertyType == MULTI_FIELD_PROPERTY,
28 "DataFrom3Dto2DSource can't be used with value properties (it can be used only with field properties)");
29};
30
32 template <typename PropertyT, typename... ExtraArgs>
33 struct DataFrom3Dto2DSourceImpl<PropertyT, FIELD_PROPERTY, VariadicTemplateTypesHolder<ExtraArgs...>>
34: public OuterDataSource<PropertyT, Geometry2DCartesian, Geometry3D, Extrusion, GeometryObjectD<3>>
35{
37 std::size_t pointsCount;
38
39 explicit DataFrom3Dto2DSourceImpl(std::size_t pointsCount = 10): pointsCount(pointsCount) {}
40
42 typedef typename PropertyAt<PropertyT, Geometry2DCartesian>::ValueType ValueType;
43
44 std::function<plask::optional<ValueType>(std::size_t index)> operator()(const shared_ptr<const MeshD<2>>& dst_mesh, ExtraArgs... extra_args, InterpolationMethod method) const override {
45 if (pointsCount > 1) {
46 const double total_len = this->outputObj->getLength();
47 const std::size_t point_count = this->pointsCount;
48 const double d = total_len / double(point_count); // first step at d/2, last at total_len - d
49 auto data = this->in(
50 plask::make_shared<CartesianMesh2DTo3DExtend>(dst_mesh, this->inTranslation, d * 0.5, total_len - d, point_count),
51 std::forward<ExtraArgs>(extra_args)..., method);
52 return [point_count, data] (std::size_t index) {
53 index *= point_count;
54 auto sum = data[index];
55 for (std::size_t i = 1; i < point_count; ++i) sum += data[index+i];
56 PLASK_NO_CONVERSION_WARNING_BEGIN
57 return PropertyT::value3Dto2D(sum / double(point_count));
58 PLASK_NO_WARNING_END
59 };
60 } else {
61 auto data = this->in(
62 plask::make_shared<CartesianMesh2DTo3D>(dst_mesh, this->inTranslation, this->outputObj->getLength() * 0.5),
63 std::forward<ExtraArgs>(extra_args)..., method);
64 return [data] (std::size_t index) { return PropertyT::value3Dto2D(data[index]); };
65 }
66 }
67};
68
70 template <typename PropertyT, typename... ExtraArgs>
71 struct DataFrom3Dto2DSourceImpl<PropertyT, MULTI_FIELD_PROPERTY, VariadicTemplateTypesHolder<ExtraArgs...>>
72: public OuterDataSource<PropertyT, Geometry2DCartesian, Geometry3D, Extrusion, GeometryObjectD<3>>
73{
75 std::size_t pointsCount;
76
77 explicit DataFrom3Dto2DSourceImpl(std::size_t pointsCount = 10): pointsCount(pointsCount) {}
78
80 typedef typename PropertyAt<PropertyT, Geometry2DCartesian>::ValueType ValueType;
81
82 typedef typename PropertyT::EnumType EnumType;
83
84 std::function<plask::optional<ValueType>(std::size_t index)> operator()(EnumType n, const shared_ptr<const MeshD<2>>& dst_mesh, ExtraArgs... extra_args, InterpolationMethod method) const override {
85 if (pointsCount > 1) {
86 const double total_len = this->outputObj->getLength();
87 const std::size_t point_count = this->pointsCount;
88 const double d = total_len / double(point_count); // first step at d/2, last at total_len - d
89 auto data = this->in(n,
90 plask::make_shared<CartesianMesh2DTo3DExtend>(dst_mesh, this->inTranslation, d * 0.5, total_len - d, point_count),
91 std::forward<ExtraArgs>(extra_args)..., method);
92 return [point_count, data] (std::size_t index) {
93 index *= point_count;
94 auto sum = data[index];
95 for (std::size_t i = 1; i < point_count; ++i) sum += data[index+i];
96 PLASK_NO_CONVERSION_WARNING_BEGIN
97 return PropertyT::value3Dto2D(sum / double(point_count));
98 PLASK_NO_WARNING_END
99 };
100 } else {
101 auto data = this->in(n,
102 plask::make_shared<CartesianMesh2DTo3D>(dst_mesh, this->inTranslation, this->outputObj->getLength() * 0.5),
103 std::forward<ExtraArgs>(extra_args)..., method);
104 return [data] (std::size_t index) { return PropertyT::value3Dto2D(data[index]); };
105 }
106 }
107
108 size_t size() const override { return this->in.size(); }
109};
110
114 template <typename PropertyT>
115 using DataFrom3Dto2DSource = DataFrom3Dto2DSourceImpl<PropertyT, PropertyT::propertyType, typename PropertyT::ExtraParams>;
116
117
118
120 template <typename PropertyT, PropertyType propertyType, typename VariadicTemplateTypesHolder>
121 struct DataFrom2Dto3DSourceImpl {
122 static_assert(propertyType == FIELD_PROPERTY || propertyType == MULTI_FIELD_PROPERTY,
123 "DataFrom2Dto3DSource can't be used with value properties (it can be used only with field properties)");
124};
125
127 template <typename PropertyT, typename... ExtraArgs>
128 struct DataFrom2Dto3DSourceImpl<PropertyT, FIELD_PROPERTY, VariadicTemplateTypesHolder<ExtraArgs...>>
129: public InnerDataSource<PropertyT, Geometry3D, Geometry2DCartesian, Geometry3D /*GeometryObjectD<3>*/, Extrusion>
130{
131 using typename InnerDataSource<PropertyT, Geometry3D, Geometry2DCartesian, Geometry3D /*GeometryObjectD<3>*/, Extrusion>::Region;
132
134 typedef typename PropertyAt<PropertyT, Geometry3D>::ValueType ValueType;
135
137 typedef typename PropertyAt<PropertyT, Geometry2DCartesian>::ValueType InputValueType;
138
139 struct LazySourceImpl {
140
141 std::vector<LazyData<InputValueType>> dataForRegion;
142
143 const DataFrom2Dto3DSourceImpl< PropertyT, FIELD_PROPERTY, VariadicTemplateTypesHolder<ExtraArgs...> >& source;
144
145 const shared_ptr<const MeshD<3>> dst_mesh;
146
147 /*std::tuple<ExtraArgs...> extra_args;
148
149 InterpolationMethod method;*/
150
151 LazySourceImpl(const DataFrom2Dto3DSourceImpl< PropertyT, FIELD_PROPERTY, VariadicTemplateTypesHolder<ExtraArgs...> >& source,
152 const shared_ptr<const MeshD<3>>& dst_mesh, ExtraArgs... extra_args, InterpolationMethod method)
153 : dataForRegion(source.regions.size()), source(source), dst_mesh(dst_mesh)/*, extra_args(extra_args...), method(method)*/
154 {
155 for (std::size_t region_index = 0; region_index < source.regions.size(); ++region_index)
156 dataForRegion[region_index].reset(source.in(plask::make_shared<ReductionTo2DMesh>(dst_mesh, source.regions[region_index].inTranslation), std::forward<ExtraArgs>(extra_args)..., method));
157 }
158
159 plask::optional<ValueType> operator()(std::size_t index) {
160 std::size_t region_index = source.findRegionIndex(dst_mesh->at(index));
161 if (region_index == source.regions.size())
162 return plask::optional<ValueType>();
163
164 /*if (dataForRegion[region_index].isNull())
165 dataForRegion[region_index].reset(source.in(plask::make_shared<ReductionTo2DMesh>(dst_mesh, source.regions[region_index].inTranslation), extra_args, method));*/
166
167 return PropertyT::value2Dto3D(dataForRegion[region_index][index]);
168 }
169
170 };
171
172 std::function<plask::optional<ValueType>(std::size_t index)> operator()(const shared_ptr<const MeshD<3>>& dst_mesh, ExtraArgs... extra_args, InterpolationMethod method) const override {
173 return LazySourceImpl(*this, dst_mesh, std::forward<ExtraArgs>(extra_args)..., method);
174 }
175
176};
177
179 template <typename PropertyT, typename... ExtraArgs>
180 struct DataFrom2Dto3DSourceImpl<PropertyT, MULTI_FIELD_PROPERTY, VariadicTemplateTypesHolder<ExtraArgs...>>
181: public InnerDataSource<PropertyT, Geometry3D, Geometry2DCartesian, Geometry3D /*GeometryObjectD<3>*/, Extrusion>
182{
183 using typename InnerDataSource<PropertyT, Geometry3D, Geometry2DCartesian, Geometry3D /*GeometryObjectD<3>*/, Extrusion>::Region;
184
186 typedef typename PropertyAt<PropertyT, Geometry3D>::ValueType ValueType;
187
189 typedef typename PropertyAt<PropertyT, Geometry2DCartesian>::ValueType InputValueType;
190
191 typedef typename PropertyT::EnumType EnumType;
192
193 struct LazySourceImpl {
194
195 std::vector<LazyData<InputValueType>> dataForRegion;
196
197 const DataFrom2Dto3DSourceImpl< PropertyT, MULTI_FIELD_PROPERTY, VariadicTemplateTypesHolder<ExtraArgs...> >& source;
198
199 const shared_ptr<const MeshD<3>> dst_mesh;
200
201 /*std::tuple<ExtraArgs...> extra_args;
202
203 InterpolationMethod method;*/
204
205 LazySourceImpl(const DataFrom2Dto3DSourceImpl< PropertyT, MULTI_FIELD_PROPERTY, VariadicTemplateTypesHolder<ExtraArgs...> >& source,
206 EnumType n, const shared_ptr<const MeshD<3>>& dst_mesh, ExtraArgs... extra_args, InterpolationMethod method)
207 : dataForRegion(source.regions.size()), source(source), dst_mesh(dst_mesh)/*, extra_args(extra_args...), method(method)*/
208 {
209 for (std::size_t region_index = 0; region_index < source.regions.size(); ++region_index)
210 dataForRegion[region_index].reset(source.in(n, plask::make_shared<ReductionTo2DMesh>(dst_mesh, source.regions[region_index].inTranslation), std::forward<ExtraArgs>(extra_args)..., method));
211 }
212
213 plask::optional<ValueType> operator()(std::size_t index) {
214 std::size_t region_index = source.findRegionIndex(dst_mesh->at(index));
215 if (region_index == source.regions.size())
216 return plask::optional<ValueType>();
217
218 /*if (dataForRegion[region_index].isNull())
219 dataForRegion[region_index].reset(source.in(plask::make_shared<ReductionTo2DMesh>(dst_mesh, source.regions[region_index].inTranslation), extra_args, method));*/
220
221 return PropertyT::value2Dto3D(dataForRegion[region_index][index]);
222 }
223
224 };
225
226 std::function<plask::optional<ValueType>(std::size_t index)> operator()(EnumType n, const shared_ptr<const MeshD<3>>& dst_mesh, ExtraArgs... extra_args, InterpolationMethod method) const override {
227 return LazySourceImpl(*this, n, dst_mesh, std::forward<ExtraArgs>(extra_args)..., method);
228 }
229
230 size_t size() const override { return this->in.size(); }
231};
232
236 template <typename PropertyT>
237 using DataFrom2Dto3DSource = DataFrom2Dto3DSourceImpl<PropertyT, PropertyT::propertyType, typename PropertyT::ExtraParams>;
238
239
240} // namespace plask
241
242#endif // PLASK__FILTER__CHANGE_SPACE_SIZE_H