/**
\page code_style Coding style

<table id="toc">
<tr>
<td>

<ul>
	<li>\ref coding_ownership</li>
	<li>\ref coding_classes</li>
	<li>\ref coding_functions</li>
	<li>\ref coding_loops</li>
	<li>\ref coding_initialization</li>
</ul>

</td>
</tr>
</table>

\section coding_ownership Ownership

When parameters are passed to functions, especially constructors,
use one of the following cases to indicate ownership:
<ul>
<li>When a function takes a copy, use <code>T &&</code>
for types that are expensive to copy. This forces callers
to pass an rvalue reference and make it explicit if they need
to provide a copy, e.g.
\code
void f(std::string &&);
void g() { std::string test{"hello"}; f(std::string(test)); }
\endcode
In cases copies are not expensive, use <code>T</code>.
</li>
<li>When a function only reads its parameter, use <code>T const &</code>.
</li>
<li>When a function takes ownership of a class that cannot be copied,
use <code>fcppt::unique_ptr<T> &&</code>.
</li>
<li>When a function keeps a reference, use <code>fcppt::reference<T></code>.
In this case, it makes it clear to the caller that he has to
keep the object alive.
</li>
<li>When a function needs shared ownership, use <code>fcppt::shared_ptr<T></code>.
This case should be considered last.
</li>
<li>Avoid regular pointers, especially <code>nullptr</code>.
</li>
</ul>

\section coding_classes Classes

Following are various points on how to design the interface of a class:
<ul>
<li>Avoid default constructors! Default constructors are usually a sign
of bad design, e.g. some code wants to assign to an object but does
not need its value. Instead of using a default constructor,
simply pass the desired values, e.g. <code>int i{0};</code>
instead of <code>int i{};</code>. If you do not have a value for
the object yet, do not create it in the first place!

There are several types which replace standard types with
the explicit intend not to be default-constructible, e.g.
#fcppt::function, #fcppt::unique_ptr,
#fcppt::shared_ptr and #fcppt::variant::object.
</li>
<li>Give every class a (non default) constructor. This ties
in with \ref coding_ownership.
Another point is that
the initialization syntax for structs and classes allows for
partial initialization, e.g.
\code
struct S { int i; int j; }; S x{42};
\endcode
However, most compilers issue a warning for this.
</li>
<li>Make classes explicitly noncopyable using #FCPPT_NONCOPYABLE
in case their copy constructors / assignment operators that are generated
by default should not be used, or in case they can not be generated
because a member is not copyable. If a class should be movable
but not copyable, explicitly provide a move constructor and move
assignment operator. Most of the time, the implementation obtained
by using <code>= default</code> can be used.
</li>
<li>Do not use regular references as members. They make a class non
assignable. Instead, use #fcppt::reference.
</li>
</ul>

\section coding_functions Functions

Following are various points about functions:
<ul>
<li>Make functions total! In case they can return nothing,
use #fcppt::optional::object.
In case they can return an error, use #fcppt::either::object.
</li>
<li>Avoid cases where certain combinations of parameters are invalid.
These cases can usually be avoided by using #fcppt::optional::object,
#fcppt::variant::object, and so on.
If it is very difficult to avoid this, it is best to throw an exception.
</li>
<li>Do not use default parameters and do not use function overloading.
It is better to provide a function with a different name or to
change the typing of parameters, e.g. by using #fcppt::optional::object.
</li>
<li>Avoid functions that get multiple parameters of the same type.
Use #fcppt::strong_typedef to disambiguate which parameter is
used for which purpose. For example, instead of
<code>void f(std::string const &name, std::string const &email);</code> use
\code
FCPPT_DECLARE_STRONG_TYPEDEF(std::string, name);
FCPPT_DECLARE_STRONG_TYPEDEF(std::string, email);
void f(name const &, email const &);
\endcode
In some cases, merging multiple parameters into one can also help,
e.g. instead of <code>void f(int x, int y);</code>, use
<code>void f(fcppt::math::vector::static_<int,2>);</code>.
</li>
<li>Do not use return parameters! In case you need to return
multiple objects, create a struct or class that encapsulates this.
</li>
</ul>

\section coding_loops Loops

Avoid explicit loops if possible. There are many cases in which
an algorithm can be used instead. For example, instead of
\snippet coding_style.cpp coding_style_loop
you can use #fcppt::algorithm::fold
\snippet coding_style.cpp coding_style_fold

Algorithms can only be used with ranges, not with iterators.
In case you need to encapsulate iterators, use <code>std::ranges::subrange</code>.
There are also special ranges like
#fcppt::int_range or #fcppt::enum_::range.
Some algorithms also accept an #fcppt::mpl::list::object as a range
in case you need to iterate over types.

\section coding_initialization Initialization

Initialize all objects and make them const if possible, especially do not use default constructors.

Provide functions for cases in which initialization can not be expressed directly.
Consider a function that initializes an array of arbitrary size:
\snippet coding_style.cpp coding_style_make_array
Say you have a function <code>T from_index(std::size_t)</code> that
creates an array element given an index. You can then initialize the array using
\snippet coding_style.cpp coding_style_array_init

In case you really need uninitialized objects, create a constructor
that takes #fcppt::no_init.
*/
