Can ‘auto’ be used in a function declaration? - c++11

Background:
I found this handy random number generator and wanted to make a header file for it:
http://www.cplusplus.com/reference/random/
std::default_random_engine generator;
std::uniform_int_distribution<int> distribution(1,6);
auto dice = std::bind ( distribution, generator );
int wisdom = dice()+dice()+dice();
However, in C++11, a function declaration with return type ‘auto’ requires a trailing return type so the compiler can decide what the type is.
E.g.:
auto foo(int a, int b) -> decltype(a*b);
Problem:
It appears like my header would need to be almost as long as the function itself to determine the type:
std::default_random_engine generator;
std::uniform_int_distribution<int> distribution(1,6);
auto roll() -> decltype(distribution(generator));
Question:
Is there a way around determining the full return type for a function declaration (in a header) that uses the ‘auto’ type?
If not, what should my dice() header look like?

Since you use int as the template type for std::uniform_int_distribution, the return type of distribution(generator) is int. Unless the real code is templated as well, then the return type could be hard-coded to int.
And if the real code is templated then you can use the result_type member of std::uniform_int_distribution:
template<typename T>
typename std::uniform_int_distribution<T>::result_type roll();
Or simply the template type itself:
template<typename T>
T roll();

Related

Remove class member type part from decltype

I ran into I case I had not seen before, while using decltype on a member of a templated class. I wanted to make a nicer make_unique so that changing type on the member does not cause fixing the make_unique calls. I wanted to avoid this using decltype(member)::element_type as the type for make_unique but got an error. Here is a simple snippet that shows the error (and I understand why it is shown):
#include <memory>
template<typename T>
struct foo
{
foo()
{
// g++ gives:
// dependent-name 'decltype (((foo<T>*)this)->foo<T>::p_)::element_type' is parsed as a non-type, but instantiation yields a type
// say 'typename decltype (((foo<T>*)this)->foo<T>::p_)::element_type' if a type is meant
//
// How can I atleast remove the class name from the type?
p_ = std::make_unique<decltype(p_)::element_type>();
// g++ gives:
// dependent-name 'decltype (p)::element_type' is parsed as a non-type, but instantiation yields a type
// say 'typename decltype (p)::element_type' if a type is meant
//
// makes sense since p here is dependent on T
std::unique_ptr<T> p = std::make_unique<decltype(p)::element_type>();
// This one is fine, makes sense, since the type is known
std::unique_ptr<int> p2 = std::make_unique<decltype(p2)::element_type>();
}
std::unique_ptr<T> p_;
};
int main()
{
foo<int> f;
return 0;
}
My question is, is there a nice/pretty way to remove the 'is a member of' ((foo<T>*)this)->foo<T>::p_))part from the decltype value, so that at least I could use the same fix and simply provide typename on the member variable p_ ? The long fix suggested by g++ seems kind of ugly.
5 minutes after posting I had an idea that I could do
p_ = std::make_unique<decltype(std::remove_reference(*p_)::type)>();
but that seems to give a parse error.
You can simply place a typename before decltype().
I mean
p_ = std::make_unique<typename decltype(p_)::element_type>();

How to use element wise integer power with Eigen

I would like to take the element wise power of an array of double with and array of int using Eigen power function.
Here is a sample code that reproduce the issue using Eigen v3.3.4 and v3.3.7:
#include <Eigen/Dense>
int main() {
Eigen::ArrayXd x(10);
Eigen::ArrayXd res(10);
Eigen::ArrayXi exponents(10);
x = Eigen::ArrayXd::Random(10);
exponents = Eigen::ArrayXi::LinSpaced(10, 0, 9);
res = Eigen::pow(x, exponents);
return (0);
}
The error message is quite long but in essence I get
YOU_MIXED_DIFFERENT_NUMERIC_TYPES__YOU_NEED_TO_USE_THE_CAST_METHOD_OF_MATRIXBASE_TO_CAST_NUMERIC_TYPES_EXPLICITLY
which does not seem appropriate to me in this context, along with
Eigen3/Eigen/src/Core/functors/BinaryFunctors.h:294:84: error: no type named ‘ReturnType’ in ‘struct Eigen::ScalarBinaryOpTraits<double, int, Eigen::internal::scalar_pow_op<double, int> >’
typedef typename ScalarBinaryOpTraits<Scalar,Exponent,scalar_pow_op>::ReturnType result_type;
As the error message indicated, you can't mix scalar types implicitly. You have to explicitly cast so that the types match:
res = Eigen::pow(x, exponents.cast<double>());
As for a specialization for integer types, the template of the power function (as a functor) is:
template<typename ScalarX,typename ScalarY, bool IsInteger =
NumTraits<ScalarX>::IsInteger&&NumTraits<ScalarY>::IsInteger>
and calls a simple pow(x,y) unless both types are integers (IsInteger), in which case there is a different specialization.
There is also an overload for an array to the power of a constant, which doesn't seem to be what you are looking for. In that case (unless ggael corrects me), you can definitely implement your own CustomBinaryOp

C++ Check if generic object has member function matching signature

first post, so hopefully not violating any etiquette. Feel free to give suggestions for making the question better.
I've seen a few posts similar to this one: Check if a class has a member function of a given signature, but none do quite what I want. Sure it "works with polymorphism" in the sense that it can properly check subclass types for the function that comes from a superclass, but what I'd like to do is check the object itself and not the class. Using some (slightly tweaked) code from that post:
// Somewhere in back-end
#include <type_traits>
template<typename, typename T>
struct HasFunction {
static_assert(integral_constant<T, false>::value,
"Second template parameter needs to be of function type."
);
};
template<typename C, typename Ret, typename... Args>
class HasFunction<C, Ret(Args...)> {
template<typename T>
static constexpr auto check(T*) -> typename is_same<
decltype(declval<T>().myfunc(declval<Args>()...)), Ret>::type;
template<typename>
static constexpr false_type check(...);
typedef decltype(check<C>(0)) type;
public:
static constexpr bool value = type::value;
};
struct W {};
struct X : W { int myfunc(double) { return 42; } };
struct Y : X {};
I'd like to have something like the following:
// somewhere else in back-end. Called by client code and doesn't know
// what it's been passed!
template <class T>
void DoSomething(T& obj) {
if (HasFunction<T, int(double)>::value)
cout << "Found it!" << endl;
// Do something with obj.myfunc
else cout << "Nothin to see here" << endl;
}
int main()
{
Y y;
W* w = &y; // same object
DoSomething(y); // Found it!
DoSomething(*w); // Nothin to see here?
}
The problem is that the same object being viewed polymorphically causes different results (because the deduced type is what is being checked and not the object). So for example, if I was iterating over a collection of W*'s and calling DoSomething I would want it to no-op on W's but it should do something for X's and Y's. Is this achievable? I'm still digging into templates so I'm still not quite sure what's possible but it seems like it isn't. Is there a different way of doing it altogether?
Also, slightly less related to that specific problem: Is there a way to make HasFunction more like an interface so I could arbitrarily check for different functions? i.e. not have ".myfunc" concrete within it? (seems like it's only possible with macros?) e.g.
template<typename T>
struct HasFoo<T> : HasFunction<T, int foo(void)> {};
int main() {
Bar b;
if(HasFoo<b>::value) b.foo();
}
Obviously that's invalid syntax but hopefully it gets the point across.
It's just not possible to perform deep inspection on a base class pointer in order to check for possible member functions on the pointed-to type (for derived types that are not known ahead of time). Even if we get reflection.
The C++ standard provides us no way to perform this kind of inspection, because the kind of run time type information that is guaranteed to be available is very limited, basically relegated to the type_info structure.
Your compiler/platform may provide additional run-time type information that you can hook into, although the exact types and machinery used to provide RTTI are generally undocumented and difficult to examine (This article by Quarkslab attempts to inspect MSVC's RTTI hierarchy)

C++11, Is it possible to force an instance to be extern but also a constant expression of a non-type template parameter?

Using C++11, g++ (GCC) 4.4.7 20120313 (Red Hat 4.4.7-18).
Lets pretend I have a templated function (pardon my terminology if it isn't quite right).
I want to perform a "general" algorithm based on what was supposed to be compile-time instances of "field". Where the only things that really changed are these constants which I moved into trait classes (only added one here but imagine there are more). Originally I was declaring it as
constexpr field FIELD1{1};
However in C++11, non-type template params need to have external linkage (unlike C++14 which can have internal and external linkage?). So because not's in the same translation unit I needed to use extern in order to give it external linkage (sorry if I butchered that explanation also). But by defining it extern I can't define it using constexpr and it seems that losing that constexpr constructor this field is no longer a valid constant expression to qualify as a non-type template param.
Any suggestions if there is some way I can get around this? Open to a new method of doing things. Below is a simplified (incomplete, and non-compiling version to get the gist of the organization).
So the error I am seeing is along the lines of
error: the value of ‘FIELD1’ is not usable in a constant expression
note: ‘FIELD1’ was not declared ‘constexpr’
extern const field FIELD1;
Not quite sure what could be a best alternative.
I can get rid of the second error by removing the constexpr from the constructor. But then I don't know how to approach the constant expression issue.
field.H
struct field
{
int thingone;
constexpr field(int i):thingone(i){}
};
extern const field FIELD1;
field.C
#include "field.H"
const field FIELD1{0};
field_traits.H
#include "field.H"
template< const field& T >
class fieldTraits;
template< >
class fieldTraits<FIELD1>
{
public:
// Let's say I have common field names
// with different constants that I want to plug
// into the "function_name" algorithm
static constexpr size_t field_val = 1;
};
function.H
#include "field.H"
template< const field& T, typename TT = fieldTraits<T> >
void function_name()
{
// Let's pretend I'm doing something useful with that data
std::cout << T.thingone << std::endl;
std::cout << TT::field_val << std::endl;
}
So because not's in the same translation unit I needed to use extern in order to give it external linkage (sorry if I butchered that explanation also). But by defining it extern I can't define it using constexpr [...]
Per my comment, you can. It wouldn't work for you, but it's a step that helps in coming up with something that would work:
extern constexpr int i = 10;
This is perfectly valid, gives i external linkage, and makes i usable in constant expressions.
But it doesn't allow multiple definitions, so it can't work in a header file which is included in multiple translation units.
Ordinarily, the way around that is with inline:
extern inline constexpr int i = 10;
But variables cannot be declared inline in C++11.
Except... when they don't need to be declared inline because the effect has already been achieved implicitly:
struct S {
static constexpr int i = 10;
};
Now, S::i has external linkage and is usable in constant expressions!
You may not even need to define your own class for this, depending on the constant's type: consider std::integral_constant. You can write
using i = std::integral_constant<int, 10>;
and now i::value will do exactly what you want.

A function with a std::function parameter does not accept a lamba function

I am trying to get more familiar with the C++11 standard by implementing the std::iterator on my own doubly linked list collection and also trying to make my own sort function to sort it.
I would like the sort function to accept a lamba as a way of sorting by making the sort accept a std::function, but it does not compile (I do not know how to implement the move_iterator, hence returning a copy of the collection instead of modifying the passed one).
template <typename _Ty, typename _By>
LinkedList<_Ty> sort(const LinkedList<_Ty>& source, std::function<bool(_By, _By)> pred)
{
LinkedList<_Ty> tmp;
while (tmp.size() != source.size())
{
_Ty suitable;
for (auto& i : source) {
if (pred(suitable, i) == true) {
suitable = i;
}
}
tmp.push_back(suitable);
}
return tmp;
}
Is my definition of the function wrong? If I try to call the function, I recieve a compilation error.
LinkedList<std::string> strings{
"one",
"two",
"long string",
"the longest of them all"
};
auto sortedByLength = sort(strings, [](const std::string& a, const std::string& b){
return a.length() < b.length();
});
Error: no instance of function template "sort" matches the argument
list argument types are: (LinkedList, lambda []bool
(const std::string &a, const std::string &)->bool)
Additional info, the compilation also gives the following error:
Error 1 error C2784: 'LinkedList<_Ty> sort(const
LinkedList<_Ty> &,std::function)' : could not
deduce template argument for 'std::function<bool(_By,_By)>'
Update: I know the sorting algorithm is incorrect and would not do what is wanted, I have no intention in leaving it as is and do not have a problem fixing that, once the declaration is correct.
The problem is that _By used inside std::function like this cannot be deduced from a lambda closure. You'd need to pass in an actual std::function object, and not a lambda. Remember that the type of a lambda expression is an unnamed class type (called the closure type), and not std::function.
What you're doing is a bit like this:
template <class T>
void foo(std::unique_ptr<T> p);
foo(nullptr);
Here, too, there's no way to deduce T from the argument.
How the standard library normally solves this: it does not restrict itself to std::function in any way, and simply makes the type of the predicate its template parameter:
template <typename _Ty, typename _Pred>
LinkedList<_Ty> sort(const LinkedList<_Ty>& source, _Pred pred)
This way, the closure type will be deduced and all is well.
Notice that you don't need std::function at all—that's pretty much only needed if you need to store a functor, or pass it through a runtime interface (not a compiletime one like templates).
Side note: your code is using identifiers which are reserved for the compiler and standard library (identifiers starting with an underscore followed by an uppercase letter). This is not legal in C++, you should avoid such reserved identifiers in your code.

Resources