
This is probably explained somewhere but, could you state what a
geometry_traits<T>::geometry_concept
is?
Luke wrote:
It is a struct that declares all functions that relate specifically to a geometry concept.
Fernando wrote: Sorry, I meant to as what a "geometry concept" is? at a entirely conceptual level. I ask becasue I can't infer the meaning from the name (to it feels as it where "lucanus_concept" :)), nor from the particular
Fernando wrote: polygon_set_concept
example.
I meant that lazy evaluation is the job of expression templates and
(and should IMO) be intrumented by an *external* general framework for
geometry_traits<T> is a metafunction for looking up the conceptual type of a geometry type T. If you pass a type which is a point type the meta function should return point_concept, if you pass a type which is a polygon type the meta function should return polygon_concept. geometry_concept is just the generic name of the return value, which is why it feels generic. In this way the geometry concept is a tag, but it is also a namespace for functions to be declared in and may eventually provide concept checking capabilities, including using those check to ensure that the arguments to the functions which should model the concept do so correctly. From that standpoint I could break it up into three different things, a tag struct, a namespace for holding functions related to the concept and a concept struct that provides concept checking capabilities. On the other hand, I really like that the tag is the namespace for passing as a template parameter and it makes sense to me to provide concept checking eventually in the following manner: struct point_concept { template <typename T> struct provides_get<T> { typedef typename result_of<point_traits<T>::get> type; }; ... template <typename T> provides_get<T> get(const T& t, orientation_2d orient) { return point_traits<T>::get(t, orient); } }; Do you think it would be better to change: geometry_traits<T>::geometry_concept to: geometry_concept<T>::type to make it more obviously a metafunction? I think I may have chosen a misleading name for it, which led to confusion. Fernando wrote: that >can that
purpose, like the pioneer PETE (http://acts.nersc.gov/pete/). IOW, this shouldn't by just an ad-hoc mechanism within some portions of your library if possible.
I'm not surprised to see that other people have implemented the same basic idea. This PETE library is exactly the solution to a problem that a colleague of mine told me he was unable to solve with C++ when I explained my expression template to him and he saw that it solves it. I suppose a generic solution for expression templates could be devised that allows a functor type to be passed as the third parameter of the template, but it would also need to add a fourth template parameter for the type for the result that needs to be allocated and passed by reference into the functor to store the result. Alternately, the operation could be required to provide a lazy iterator output semantic. At that point, however, it is more generic than most people need and I fear that if such a library existed it wouldn't be very used. This is what I have in mind: template <typename l_type, typename r_type, typename functor_type, typename result_type> class lazy_evaluation { private: mutable result_type result_; mutable bool evaluated_; const l_type& lvalue_; const r_type& rvalue_; public: lazy_evaluation(const l_type& lvalue, const r_type& rvalue) : lvalue_(lvalue), rvalue_(rvalue), evaluate_(false) {} //needs to be declared const so callable from a //const reference to this const result_type& evaluate() const { //prevent redundant evaluation if(!evaluated_) { //modifies mutable result, which stores the //result of evaluation functor_type()(result_, lvalue_.evaluate(), rvalue_evaluate()); //modifies mutable evaluated member data evaluated_ = true; } return result_; } }; which factors out the expression template from my usage of it. It might make sense for me to refactor my code in this way to provide the abstraction between functor and expression template to eliminate specialization of the expression template. It may also prove useful when I implement mixed operations between axis-parallel and arbitrary angle geometry types in which the algorithms and operators selected will depend on the conceptual types of the input operands and I will need to apply the same pattern several times over. I'll need to think about it more. Thanks, Luke