On Wed, 15 Apr 2020 at 15:28, Arthur O'Dwyer via Std-Proposals <std-proposals@lists.isocpp.org> wrote:
On Tue, Apr 14, 2020 at 11:23 PM JeanHeyd Meneide via Std-Proposals <std-proposals@lists.isocpp.org> wrote:
On Tue, Apr 14, 2020 at 9:52 PM Mario Charest via Std-Proposals <std-proposals@lists.isocpp.org> wrote:
...
What is the rational for std::span not having an at() fonction, like most other contiguous container.

Because at() is a mistake for string view and all other cheap view types; that we made the mistake with string_view is unfortunate.

There are two problems with at() as a member function, today.

(The first is its design — nit: I don't think this is a "problem"; I think this is "your preferred solution to the second problem." Me personally, I definitely want it to be a member function, for ergonomics; and I would want it to work on any random-access range, even `deque`. I would also want some exploration of the existing std::map facility: should m.at(idx) mean (idx < m.size() ? m[idx] : throw out_of_range()), and if not, why not? Generic programming requires extracting the commonalities between different possible parameter types, and I don't think that work is entirely done yet.)

It sounds like you want the (UFC?) syntax but that's different to justifying membership. There are good reasons to prefer free functions to member functions. Numerous sources (such as the CCG and H&A's C++ Coding Standards) do a good job of explaining them. That many users like their 'dot' style is not sufficient reason to perpetuate the design error that led to, e.g., string's bloated API.

     The second is the contention that comes from C++'s exceptions burden. One of the biggest problems (and biggest benefits) of at() is that it throws an exception on out-of-bounds. This is cute and nice and wonderful, save for that in C++ this means bringing in a dependency on using "throw", and throwing a standard exception. All standard exceptions defined in the standard library -- out_of_range(), for example -- have a constructor that takes a std::string, because the string view technology wasn't there yet.

This WOULD cost every person using the span header enormously

There may be an additional lack of appetite for `at` because it is seen as a facility which is often abused to deal with bugs, for which contracts are the correct mechanism.

my €.02,
John