On 2011-06-11 20:27, Andrei Alexandrescu wrote: > On 06/11/2011 03:52 PM, Nick Sabalausky wrote: > > "Andrei Alexandrescu"<seewebsiteforem...@erdani.org> wrote in message > > news:it07ni$1pvj$1...@digitalmars.com... > > > >> Anyway, that was the first thing "grep yes std/*" found. Let's see the > >> next one: > >> > >> /** > >> Specifies whether the output of certain algorithm is desired in sorted > >> format. > >> > >> */ > >> > >> enum SortOutput { > >> > >> no, /// Don't sort output > >> yes, /// Sort output > >> > >> } > >> > >> This already is very unpleasant because "certain" is as imprecise as it > >> gets. Plus one for Flag, I hope you agree. > > > > Flag -= 1 > > s/output of certain algorithm/output of an algorithm/ += 1 > > > > That one-word doc change makes it all perfectly clear. > > Not at all. The typo in the original text must have confused you: it > should be "certain algorithms" because SortOutput is used in four > distinct algorithms (one of which has two overloads). Grep std/algorithm.d. > > Flag += 2 > > > Also, since you're in favor of Flag, I think you'd agree with me that the > > doc comments on the "no" and "yes" values are unnecessary and can be > > ditched. Which makes the whole idiom this: > > > > enum SortOutput { no, yes } > > This exact kind of argument has been made in 1995 in favor of STL > algorithms that require defining a struct outside the current context. > The cost of adding one extra symbol turned out to be a fair amount more > unpleasant than it was initially though. > > Assessing that the boilerplate in this case is one line would be missing > that important aspect.
Yes, though there is a distinct difference between having to create a functor elswhere to just to call an STL function and creating an extra enum next to your function definition for one of its parameters. The parameter issue is far smaller IMHO. It only comes up when defining functions, and particularly if we created a mixin for creating such an enum, the overhead would be fairly minimal - certainly far less than creating a functor for every call to an STL algorithm function (which pratically destroys the usefulness of the STL's algorithms for most people). So, I don't think that the cost involved is altogether comparable. However, you do bring up a very valid point. Flag definitely lowers the bar for the usage of such enums. Ultimately, my main concern with using Flag like this is the error messages. Given the templates involved, I'd expect them to be pretty bad. D's template error messages are certainly better than C++'s (primarily thanks to template constraints), but they're still pretty bad - especially for newbies - and this particular use case effectively is simplifying the library developer's life slightly at the cost of nastier error messages for everyone who mistypes one of these enums. So, we save pain in one area and move it over to another which arguably has a higher impact. And I'm just not sure whether that's worth it or not. The fact that you've gotten to Yes.EnumName and eliminated all of the obvious template stuff from the user's perspective makes the code much cleaner, and it's fine as long as they don't have any typos, but the difference between EnumName.yes and Yes.EnumName for the user is pretty much nonexistant except for the fact that Yes.EnumName will have worse error messages. So, from the user's perspective, the situation is worse. I don't know. I think that this proposal has reached the point where it might be reasonable to include it, but I just don't know if the gain in development is worth the pain for everyone who uses the functions which have Flag enums. If the error messages weren't worse, then it wouldn't be a problem, but as soon as you include templates, the error messages are pretty much always significantly worse. If there were a significant gain from this proposal, then I'd say that it would be worth it, but the gain seems pretty minor to me. So, I just don't know. - Jonathan M Davis