I am a avid emacs user, and want to use sgml markup check routine.
I was naturally headed towards nsgmls, and downloded the source code to compile it.
However, there was a strange error coming from the compiler with the followings.
./../include/RangeMap.h:57: error: type ‘Vector<RangeMapRange<From, To> >’ is not deri ved from type ‘RangeMapIter<From, To>’
./../include/RangeMap.h:57: error: expected ‘;’ before ‘ptr_’
./../include/RangeMap.h: In member function ‘Boolean RangeMapIter<From, To>::next(From&, From&, To&)’:
./../include/RangeMap.h:47: error: ‘ptr_’ was not declared in this scope
I know that some times compiler gets disgruntled by template and typename madness, however the codes seems to have already used typename correctly within the code.
Here are the cope snippets that arouses these errors.
template<class From, class To>
class RangeMapIter {
public:
RangeMapIter(const RangeMap<From,To> &map);
Boolean next(From &fromMin, From &fromMax, To &toMin) {
if (!count_)
return 0;
else {
fromMin = ptr_->fromMin;
fromMax = ptr_->fromMax;
toMin = ptr_->toMin;
ptr_++;
count_--;
return 1;
}
}
private:
size_t count_;
typename Vector<RangeMapRange<From,To> >::const_iterator ptr_;
};
Can anybody help me hash out those errors?
This error message is given by GCC in the wrong order of both type names. (but it apparently fixed this in the latest version). It is meant to say that Vector<RangeMapRange<From,To> >::const_iterator was not found to be a type name. The underlying cause of this diagnostic is that the code is parsed as an access-declaration, which has the following syntax
::[opt] nested-name-specifier template[opt] unqualified-id ;
An example of that syntax
struct A {
int a;
};
struct B : A {
// equivalent to: using A::a;
A::a;
};
In C++11 this access-declaration construct was taken out of the specification and it was deprecated in C++03. But since the compiler still supports parsing it, when the Vector<RangeMapRange<From,To> >::const_iterator is not found to be a type, it will be taken as a name to be declared in an access-declaration (so the parser moves forward across the type specifier section). Hence according to the above syntax, after the unqualified-id which in this case is const_iterator (and in my example was a), it wants to see a semicolon and it wants that Vector<RangeMapRange<From, To> > is a base class of RangeMapIter<From, To>, but confusingly the diagnostic it gives has it the other way around.
Check your names and make sure the type exists.
Related
While working on my class declaration I'm having some confusion on how to use alias templates and template variables within in a non class template while trying to use auto type deduction.
Signal.h
#ifndef SIGNAL_H
#define SIGNAL_H
#include <cstdint>
template<typename T>
using TimeSignal = T;
using DiscreteTime = TimeSignal<std::uint8_t>;
using ContinuousTime = TimeSignal<double>;
class Signal {
private:
template<typename T>
static TimeSignal<T> time_;
double voltage_;
double current_;
public:
template<typename T>
explicit Signal( TimeSignal<T> time, double voltage = 0, double current = 0 ) :
voltage_{voltage}, current_{current}
{ time_ = time; }
double sampleVoltage() { return voltage_; }
double sampleCurrent() { return current_; }
template<typename T>
static auto atTime() { return time_; }
};
#endif // SIGNAL_H
And I would be using it like this:
#include <iostream>
#include "Signal.h"
int main() {
DiscreteTime t1{ 5 };
ContinuousTime t2{ 7.5 };
Signal s1{ t1, 3.5, 0.05 );
Signal s2{ t2, 4.3, 0.09 );
auto time1 = s1.atTime();
auto time2 = s2.atTime();
return 0;
}
I don't want to template this class, so I was thinking about having an internal variable template. Outside of the class I was trying to use a template alias to have the different "TimeSignals" be descriptive as a "DiscreteTime" is typically and integral type and a ContinousTime is a floating point or over the set of Real numbers. I was however templating the constructor of this class that takes in the TimeSignal type and wanted the class to deduce the or to auto resolve it's internal variable template to that type depending which of the two types were passed in. Finally I was trying to use auto type deduction to return that type.
I don't know if its the syntax or the usage but this has me stumped. I'm not sure how to get this to a working compile state.
This is the current compiler errors that Visual Studio 2017 is giving me.
1>------ Build started: Project: Circuit Maker Simulator, Configuration: Debug x64 ------
1>main.cpp
1>c:\...\main.cpp(15): error C2672: 'Signal::atTime': no matching overloaded function found
1>c:\...\main.cpp(15): error C2783: 'auto Signal::atTime(void)': could not deduce template argument for 'T'
1>c:\...\Signal.h(64): note: see declaration of 'Signal::atTime'
1>c:\...\main.cpp(24): error C2672: 'Signal::atTime': no matching overloaded function found
1>c:\...\main.cpp(24): error C2783: 'auto Signal::atTime(void)': could not deduce template argument for 'T'
1>c:\...\Signal.h(64): note: see declaration of 'Signal::atTime'
1>Done building project "Circuit Maker Simulator.vcxproj" -- FAILED.
The compiler error's obvious to what they are saying, but it's like they are screaming or yelling at me without any help, assistance or suggestions on how to fix or resolve this...
Edit
User rafix07 helped me quite a bit with his answer and it was helpful. I was missing a couple of things, two of them I may have eventually caught onto if I kept staring at it long enough and that was the use of the variable templates within the class needing it's template argument or parameter. The other was using the scope resolution operator in the main function to call the static function. I could of found them given some time.
The one issue that had me stumbling in circles was the fact that I had to explicitly instantiate the function template of the type I want when calling it. This is the one that would of had me pulling out my hair for ours...
After adjusting the code according to the link in his answer I'm now able to compile, however I am now getting linker errors for unresolved external symbols and it has to do with the template variables. Which shouldn't be a problem, just need to define it within a cpp file to resolve static variables.
First of all, atTime is static method so only way to call it is to use scope resolution operator ::. atTime takes no arguments, so T cannot be deduced, and you need to put type in template arguments list explicitly:
auto time1 = Signal::atTime<DiscreteTime>();
auto time2 = Signal::atTime<ContinuousTime>();
In ctor of Signal and atTime function you have to specify T for which variable template is accessed:
template<typename T>
explicit Signal( TimeSignal<T> time, double voltage = 0, double current = 0 ) :
voltage_{voltage}, current_{current}
{ time_<T> = time; }
Full working code is here.
This question already has an answer here:
Operator cast, GCC and clang: which compiler is right?
(1 answer)
Closed 6 years ago.
Consider following program:
struct S {
using T = float;
operator T() { return 9.9f; }
};
int main() {
S m;
S::T t = m;
t = m.operator T(); // Is this correct ?
}
The program compiles fine in g++ ( See live demo here )
But it fails in compilation in clang++, MSVC++ & Intel C++ compiler
clang++ gives following errors ( See live demo here )
main.cpp:8:20: error: unknown type name 'T'; did you mean 'S::T'?
t = m.operator T(); // Is this correct ?
^
S::T
main.cpp:2:11: note: 'S::T' declared here
using T = float;
MSVC++ gives following errors ( See live demo here )
source_file.cpp(8): error C2833: 'operator T' is not a recognized operator or type
source_file.cpp(8): error C2059: syntax error: 'newline'
Intel C++ Compiler also rejects this code ( See live demo here )
So, the question is which compiler is right here ? Is g++ incorrect here or other 3 compilers are incorrect here ? What C++ standard says about this ?
[basic.lookup.classref]/7:
If the id-expression is a conversion-function-id, its conversion-type-id is first looked up in the class of the object expression and the name, if found, is used. Otherwise it is looked up in the context of the entire
postfix-expression. In each of these lookups, only names that denote types or templates whose specializations are types are considered. [ Example:
struct A { };
namespace N {
struct A {
void g() { }
template <class T> operator T();
};
}
int main() {
N::A a;
a.operator A(); // calls N::A::operator N::A
}
— end example]
This indicates that the example could be fine, although in the above example, A has previously been declared as a type name, visible to main.
This was discussed in core issue 156, filed all the way back in 1999:
How about:
struct A { typedef int T; operator T(); };
struct B : A { operator T(); } b;
void foo() {
b.A::operator T(); // 2) error T is not found in the context
// of the postfix-expression?
}
Is this interpretation correct? Or was the intent for this to be an
error only if T was found in both scopes and referred to different
entities?
Erwin Unruh: The intent was that you look in both contexts. If you find it only once, that's the symbol. If you find it in both, both symbols must be "the same" in some respect. (If you don't find it, its an error).
So I'd say that Clang is wrong: the intent, as expressed in the wording to some extent, is that we find T, even if only in the class.
I have the following code:
typedef bool (A::*rule)(shared_ptr<Node >, shared_ptr<Node> ) ;
when initilaising the class A object, I run the following code
v_ = vector<rule>();
v_.push_back(A::memberFunction);
I have also tried with v_.push_back(&A::memberFunction) as this seemed more logical to me, but was
advised against on the forums. I also get an error message
This is as suggested by the many topics on the matter. However, I get the following error
non-const lvalue reference to type 'value_type' (aka 'bool (boost::shared_ptr<Node>, boost::shared_ptr<Node>)')
cannot bind to a temporary of type '<bound member function type>'
Does anyone know where I am going wrong?
I have also tried with v_.push_back(&A::memberFunction) as this seemed more logical to me, but was advised against on the forums.
I don't know what forums were those. Forming a pointer-to-member has a single valid syntax, and it is & classname::membername. All elements mandatory.
Use that consistently and post code and error message for that version should the problem persist.
This code compiles under llvm/clang 4.2 (As #balog-pal said, the & is mandatory before classname::membername:
#include <memory>
#include <vector>
struct Node {};
struct A
{
bool rule(std::shared_ptr<Node>, std::shared_ptr<Node>)
{return true;}
};
typedef bool (A::*rule)(std::shared_ptr<Node>, std::shared_ptr<Node> );
int main(int, const char**)
{
std::vector<rule> v;
v.push_back(&A::rule);
return 0;
}
Please post a full not-compiling example, your issue must be hidden somewhere else.
I am trying to understand how to best make use of blocks in my templated class.
I have the following code snippet:
template<typename T, typename R>
class MyClass {
public:
typedef R (^Block)(T);
MyClass(Block blk) {}
};
void testMyClass() {
MyClass<int,int>::Block blk(^(int arg) {
return 1 + arg;
});
}
When I try to compile this, I get the following error message:
error: cannot convert ‘int (^)(int)’ to ‘R (^)(T)’ in initialization
Am I missing something obvious? Am I trying to do something that is not allowed? GCC accepts the program if I do the same thing without templates.
This is an issue in GCC. I tested your program under LLVM 3 and it compiled just fine.
There are a number of problems in GCC 4.2's implementation of blocks, sometimes they can be worked around by fully qualifying your block declarations ^int(int arg){return 1 + arg;} but in this case it was unable to work around this issue. I would highly recommend moving to use LLVM/Clang for any further work with Obj-C Blocks. Its C++ support is very good these days, especially for C++03 support.
FC++ is a library for functional programming in C++. I am using it on MinGW with gcc 4.5.0. When I use the more basic features, I have no problems. But one of the more advanced features is giving me a template-related error (or maybe there's just a problem with my code...couldn't be!).
Does anybody have FC++ working with 4.5.0? See anything wrong with my code?
The link text is solidly out of date, though it shows a history of issues with gcc and template specialization. The link text isn't more up to date.
Here's my code:
#include <iostream>
#include "prelude.h"
using namespace fcpp;
using namespace std;
struct TwoTimes {
template <class T>
struct Sig : public FunType<T,T> {};
template <class F>
F operator() (const F& x) const { return 2*x; };
} twoTimes;
int main(int argc, char* argv[] )
{
cout << compose(twoTimes,twoTimes)(3) << endl;
return 0;
}
The error I get is:
In file included from full.h:14:0,
from lambda.h:38,
from operator.h:29,
from function.h:23,
from reuse.h:14,
from list.h:31,
from prelude.h:32,
from y.cxx:2:
smart.h: In instantiation of 'fcpp::FunctoidTraits<TwoTimes>':
prelude.h:142:74: instantiated from 'fcpp::impl::XCompose::Sig<TwoTimes, TwoTimes>'
full.h:94:53: instantiated from 'fcpp::Full2<fcpp::impl::XCompose>::Sig<TwoTimes, TwoTimes>'
y.cxx:18:46: instantiated from here
smart.h:103:7: error: no type named 'Type' in 'struct
fcpp::impl::NeededASmartFunctoidButInsteadGot<TwoTimes, false>'
In file included from y.cxx:2:0:
prelude.h: In instantiation of 'fcpp::impl::XCompose::Sig<TwoTimes, TwoTimes>':
full.h:94:53: instantiated from 'fcpp::Full2<fcpp::impl::XCompose>::Sig<TwoTimes, TwoTimes>'
y.cxx:18:46: instantiated from here
prelude.h:142:74: error: 'fcpp::FunctoidTraits<TwoTimes>::max_args' is not a valid
template argument for type 'int' because it is a non-constant expression
In file included from lambda.h:38:0,
from operator.h:29,
from function.h:23,
from reuse.h:14,
from list.h:31,
from prelude.h:32,
from y.cxx:2:
full.h: In instantiation of 'fcpp::Full2<fcpp::impl::XCompose>::Sig<TwoTimes, TwoTimes>':
y.cxx:18:46:
instantiated from here
full.h:94:53: error: no type named 'Arg1Type' in 'struct
fcpp::impl::XCompose::Sig<TwoTimes, TwoTimes>'
y.cxx: In function 'int main(int, char**)':
y.cxx:18:46: error: no match for call to '(fcpp::Compose) (TwoTimes&, TwoTimes&)'
Well .... the links you refer to are seven years old. In dog and compiler years, that is a good lifetime.
If you want functional programming with (current) C++ compilers, maybe some of the Boost libraries may be of interest?
If the answer is still needed to this, the struct TwoTimes needs to be wrapped to work with FC++. I have worked a lot with FC++ over several years. The best thing I can do is point to here on the C2 wiki where I have discussed this:
http://c2.com/cgi/wiki?FunctoidsInCpp
Any posting there I will see.