
From: vicente.botet
* I find that the extreme example "bounded object with memory" is not a good example of constrained_value because not constrained at all.
Yes, as I have already explained, this is not supposed to be a typical ("good") example. This is supposed to be an "extreme" example. The introduction to the examples section says "In this section you will find some more advanced, useful or crazy examples of what can be done using the library. For introductory examples, see Tutorial section." and I think this example fits there well.
I don't understand why an error policy can modify the value or the constraint. I would prefer an error policy taking only two in-parameters (by value or const&) the new value and the constraint.
I have already answered to this in the other post.
* The wrapping and cliping classes are not exactly constrained values, they are adapting a value of a type to a constrained value.
Ditto.
* I don't know if you will add monitored values to your library. IMO it will be better to have them in a separated class.
Or, if it's reasonable, implement constrained objects in terms of monitored objects.
We can monitor values that are constrained or not. "bounded object with memory" could be better considerd as a monitored value.
I agree.
* The class bounded_int should take another name as e.g. static_bounded.
This may be a confusing name too. I'd rather name a class using static within_bounds predicate as static_bounded (something similar to what Jesse Perla was asking for on the users group).
* I dont like the free functions to change the constraints as change_lower_bound. I think that it is preferable to have specific classes and no typedefs. Classes as bounded can define the specific operations for changing the bounds.
I disagree here. This would mean unnecessary duplication of code and I'm definitely opponent of it.
* The operators have not always a sens for the application. For example, constrained<int, is_even> x; ++x;
I would prefer to have a compile error in this particular case instead of an exception. It will be quite interesting to show how a user can catch this error at compile time and avoid this runtime error.
Passing over presumable complexity of the implementation, this would be quite inconsistent behaviour. Why "++x" should behave in a different way than "x += 1"? What if the user wants this to be a runtime error or wants to use the object in a generic function (wich would contain the "++x" expression, but not necessarily invoke it)?
template<typename V , typename C , typename E > constrained< V, C, E , with_arithmetic_operators> & operator++ (constrained< V, C, E,with_arithmetic_operators> &c)
the bounded hierarchy should have with_arithmetic_operators.
Then for the even object we should also ban, e.g., *=, although it perfectly makes sense?
* constrained must be default constructible. The library should provide a mean to specify a default value. E. g. constrained<default<int, 1>, is_odd >
I think this is too general utility to belong to this library (it's similar to value_initialized in Boost.Utility).
* The default value for excluding the bound is false, which mean that the bound is included. There is no example of excluding bounds. Here is one
What do you exactly mean by saying "there is no example"? The tutorial contains a section titled "Bounded objects with open ranges".
I think that it will more clear if instead of stating exclusion we state inclusion, and the default be true,
So we can write typedef static_bounded<int, 0, 100, throw_exception<>, false, true>::type t;
A value-initialised bool has the value of false. Therefore, bounds exclusion is used rather than bounds inclusion, so the default is always "bounds included" when the bounds inclusion indicators are default-constructed.
* I would like the library manage constraints between several variables, e.g the range of valid days values depends on the month. We can need to set/get each varaible independently or all at once. The concept of tuple seems interesting.
Indeed, sounds interesting, but I wonder if it would be needed frequently enough to make this part of the library.
The current interface could also be used as
typedef constrained<tuple<day, month>, adapt_day_to _month_constraint > date;
but we can not assign the value independently.
That's right. What I'd rather do is to define a simple class containing the constrained day and month, and providing functions to get/set the members. The setter for the month would additionally adjust the upper bound of the day.
Of course the user can implement hisself the constrained_tuple class. If I have time I will try to implemnet it.
If you do, I'd love to hear from you how did it go.
* The number of parameters of the bounded class is already to high.
Most of them (ordered from most to least used) have default values, so I don't think this is a serious problem. Your solution reduces them from 7 to 5, which may be seen as not much... However, it looks interesting.
Even in this case the bool values are not enough declarative. It would even be beter to define two templates, open, close (see below) typedef static_bounded<int, open<0>, close<100> >::type t;
I don't know if this is an optimal solution if for the most common case, when the bounds are included, you have to write more than: typedef static_bounded<int, 0, 100>::type t;
Adding more examples will be welcome as: * Application domain classes using (by inheritance and by containement) a constrained class to see what the user needs to do when it needs to add some methods, and don't want some inherited methods.
I don't know if such example is indeed needed, sounds a bit like showing how to derive from std::string...
*Date type would show the change upper bound at runtime, and see how the values of a variable (month) impact the constraints on another variable (day).
Might be a nice example, let me consider this.
*The example of a low static bounded and runtime dynamic bounded could be a good one to show how the constrained class can be specialized.
Ditto.
- How much effort did you put into your evaluation? A glance? A quick reading? In-depth study? In-depth study of the documentation, implementation and the review posts.
Thanks for your time for the review and the discussions. Best regards, Robert