Errors within .h and main

Okay, I'm working on an assignment that is supposed to accept input as roman numerals and convert it to decimal form. I'm supposed to create it as a class and implementation and main files. Here are the errors I'm getting(bear in mind, none of the errors are in the Imp code):

4 Q:\USB Files\USB Files\Spring 2014\C++ Homework\Session 4\main.cpp In file included from main.cpp
4 Q:\USB Files\USB Files\Spring 2014\C++ Homework\Session 4\romanType.h variable or field `verifyInput' declared void
4 Q:\USB Files\USB Files\Spring 2014\C++ Homework\Session 4\romanType.h expected `;' before '(' token
Q:\USB Files\USB Files\Spring 2014\C++ Homework\Session 4\main.cpp In function `int main()':
19 Q:\USB Files\USB Files\Spring 2014\C++ Homework\Session 4\main.cpp `verifyInput' is not a member of `romanType'
21 Q:\USB Files\USB Files\Spring 2014\C++ Homework\Session 4\main.cpp `convertDecimal' is not a member of `romanType'
Q:\USB Files\USB Files\Spring 2014\C++ Homework\Session 4\Makefile.win [Build Error] [main.o] Error 1

Here is my main code

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
#include <cstdlib>
#include <iostream>
#include <string>
#include "romanType.h"


using namespace std;

int main()
{
    
    string roman;
    
    cout << "please enter a roman numeral character(s)" ;
    cin >> roman;
    
    
    
    romanType::verifyInput(roman);
    
    cout << "Decimal of " << roman << " is " << romanType::convertDecimal(roman);
    
    return 0;
    
    system("PAUSE");
}


Here is my .h code

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
class romanType
{ 
public:
             void verifyInput(string)
             void convertDecimal(string)
             void printDecimal() const

      
private:
              string romanNumeral;
              int decimal;
      
};



And here is my Imp code

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
#include <string>
#include <iostream>
#include "romanType.h"
using namespace std;


      void romanType::verifyInput(string roman)
{     
      romanNumeral = roman; 
      romanNumeral.toupper; 
      int length = romanNumeral.length();
      for (int count = 0; count < length; count++)
          string sub = romanNumeral.substr(count, count);
          if (sub != "I" || sub != "V" || sub != "X" || sub != "L" || sub != "C" || sub != "D" || sub != "M")
              cout << "Error. Invalid input"<< endl;      
}

      void romanType::convertToDecimal(string roman)
{
      
	  for (int i = 0; i < roman.length(); i++ )

		switch (roman[i])
		{
			case 'M': decimal += M; break;
			case 'D': 
                                 if(i + 1 != roman.size() &&roman[i+1] == 'M')
                                        decimal -= D;
                                 else
                                        decimal += D; break;
			case 'C': 
                                 if (i + 1 != roman.size() && roman[i+1] == 'M' || roman[i+1] == 'D')
                                        decimal -= C;
                                 else
                                        decimal += C; break;
			case 'L':
                                 if (i + 1 != roman.size() && roman[i+1] == 'M' || roman[i+1] == 'D' || roman[i+1] == 'C')
                                        decimal -= L; break;
                                 else
                                        decimal += L; break;
			case 'X':
                                 if (i + 1 != roman.size() && roman[i+1] == 'M' || roman[i+1] == 'D' || roman[i+1] == 'C') || roman[i+1] == 'L')
                                        decimal -= X; break;
                                 else
                                        decimal += X; break;
			case 'V':
                                 if (i + 1 != roman.size() && roman[i+1] == 'M' || roman[i+1] == 'D' || roman[i+1] == 'C') || roman[i+1] == 'L') || roman[i+1] == 'X')
                                        decimal -= V; break;
                                 else
                                        decimal += V; break;
			case 'I':
                                 if ( i + 1 != roman.size() && roman[i + 1] != 'I')
					                    decimal-=1;
                                 else
					                    decimal+=1;
}
     void romanType::printDecimal()
{
     cout << "Your roman numeral is converted to " << decimal;
}



Thanks for any help! I did steal (borrow?) some code off of another post on here :)
Last edited on
romanType.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
#pragma once //header guards
#ifndef ROMAN_TYPE_H
#define ROMAN_TYPE_H

#include <string> //make it self contained
class romanType
{ 
public:
             void verifyInput(std::string); //semicolon. Also string lives in the std namespace
             void convertDecimal(std::string);
             void printDecimal() const;

      
private:
              std::string romanNumeral;
              int decimal;
};
#endif 
Thank you for your help ne555. After trying your code, I get the error :

16 Q:\USB Files\USB Files\Spring 2014\C++ Homework\Session 4\main.cpp cannot call member function `void romanType::verifyInput(std::string)' without object

18 Q:\USB Files\USB Files\Spring 2014\C++ Homework\Session 4\main.cpp cannot call member function `void romanType::convertDecimal(std::string)' without object
1
2
3
4
5
6
7
8
9
int main()
{
//...    
    romanType caesar; //creating an object
    caesar.verifyinput(roman); //calling the method on the object
    
    cout << "Decimal of " << roman << " is " << caesar.convertDecimal(roman);
//...
}
Ok, I have most of this cleared up. The only problem I'm having now is linker errors @ romanType::printDecimal(). Also, verifyInput is saying input is invalid even though it is not. So for instance, I input v or V it says it is invalid. Any other suggestions? Thanks ahead of time!

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
#include <string>
#include <iostream>
#include "romanType.h"
using namespace std;


      void romanType::verifyInput(string roman)
{     
      string sub;
      romanNumeral = roman;  
      int length = romanNumeral.length();
      for (int count = 0; count < length; count++)
          sub = romanNumeral.substr(count, count);
          if (sub != "I" || sub != "V" || sub != "X" || sub != "L" || sub != "C" || sub != "D" || sub != "M")
              cout << "Error. Invalid input"<< endl;  
              system("Pause");    
}

      void romanType::convertDecimal(string roman)
{
      enum values{ M = 1000, D = 500, C = 100, L = 50, X = 10, V = 5, I = 1};
	  for (int i = 0; i < roman.length(); i++ )

		switch (roman[i])
		{
			case 'M': decimal += M; break;
			case 'D': 
                                 if(i + 1 != roman.size() &&roman[i+1] == 'M')
                                        decimal -= D;
                                 else
                                        decimal += D; break;
			case 'C': 
                                 if (i + 1 != roman.size() && roman[i+1] == 'M' || roman[i+1] == 'D')
                                        decimal -= C;
                                 else
                                        decimal += C; break;
			case 'L':
                                 if (i + 1 != roman.size() && roman[i+1] == 'M' || roman[i+1] == 'D' || roman[i+1] == 'C')
                                        decimal -= L;
                                 else
                                        decimal += L; break;
			case 'X':
                                 if (i + 1 != roman.size() && roman[i+1] == 'M' || roman[i+1] == 'D' || roman[i+1] == 'C' || roman[i+1] == 'L')
                                        decimal -= X;
                                 else
                                        decimal += X; break;
			case 'V':
                                 if (i + 1 != roman.size() && roman[i+1] == 'M' || roman[i+1] == 'D' || roman[i+1] == 'C' || roman[i+1] == 'L' || roman[i+1] == 'X')
                                        decimal -= V;
                                 else
                                        decimal += V; break;
			case 'I':
                                 if ( i + 1 != roman.size() && roman[i + 1] != 'I')
					                    decimal-=1;
                                 else
					                    decimal+=1; break;
}
     romanType::printDecimal();
{
     cout << "Your roman numeral is converted to " << decimal;
}
}

well I don't see the definition for the print decimal function. Also you can simply put printDecimal(); there is no need to scope when you are already inside the class. Sorry the problem is that you forgot the return type (void) also it is a const function so you should put that also and remove the semicolon. As for your input you say if the output is not one of the letters then it is an error. It should be if the input is not any of the allowed one. So if (sub != "I" || sub != "V" || sub != "X" || sub != "L" || sub != "C" || sub != "D" || sub != "M") you should replace the comparison or || with comparison and &&

* a few more things to mention you are missing the closing brace to the switch and it looks like you are defining the print function inside of the convert. So you may want to move the braces around like this:

1
2
3
4
5
6
        }
}
void romanType::printDecimal() const
{
     cout << "Your roman numeral is converted to " << decimal;
}
Last edited on
Thanks for the input! I'm going to implement it tomorrow and see where I'm at! I appreciate all of the help on this forum. I shouldn't have waited a year to take my advanced c++ class. Probably shouldn't have taken it online either :P
Ok, have it all worked out and compiling fine. I'm still having the same problem in the comparison though. It doesn't seem to make a difference if I do or || or and && Is there something wrong with the logic in the code? It seems right to me, but an extra set of eyes always helps.
Well you will want to use the and operator not or. The problem is sub = romanNumeral.substr(count, count); you want to only get 1 character so it should be sub = romanNumeral.substr(count,1);
http://www.cplusplus.com/reference/string/string/substr/

Also you are going to have to be careful that there are no spaces besides
IVXLCDM
or it will say there is an error.
Last edited on
Ahhhh, OK, got it. One last post then I will leave everyone alone for a while :) Now, it does everything fine, except output the proper number. So if I put in, X it spits out 5443202 the first time, but if I put in X again it spits out 6033026. It's not producing the correct values and the values it does produce are not consistent.
Did you ever initialize decimal it sounds like it has not been initialized in this case you will want to default value to be 0. You don't have a constructor looking back so when you call the convertDecimal function you are going to want to set the decimal to 0.
1
2
3
4
5
6
7
void romanType::convertDecimal(string roman)
{
    decimal = 0; //give it a starting value
    enum values{ M = 1000, D = 500, C = 100, L = 50, X = 10, V = 5, I = 1};
   
    //...
}
That was it! I thought I tried that and it spit an error out...Maybe not. Either way, I appreciate it! Thanks to everyone who helped!
Hi,

Just going to bust in here a bit.

I really hate dislike constructs like this:

if (sub != "I" && sub != "V" && sub != "X" && sub != "L" && sub != "C" && sub != "D" && sub != "M")

EDIT: See ne555 far superior solution below.

A much tidier alternative IMO is a switch without breaks for the first example on line 14 of your code:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
//changed return type  to bool
bool romanType::verifyInput(std::string RomanInput) {

    
    std::string RomanNumeral = "a"; //A single char from the input

    for (int Position = 0; Position < RomanInput.length; ++Position ) { //always use braces
         RomanNumeral = RomanInput.substr(Position , 1); //1 char at a time

         switch (RomanNumeral ) {
            case "I" : case  "V" : case "X"
            case "L" : case "C" : case "D" : case "M"
     
           default :
               return false;
               break;

        }
    }
    return true;
}





Now in main() you can have some code that tests the results of verifyInput and takes the correct action. Could put this code in a while loop.

For your switch lines 24 - 57, each case can have it's own switch similar to the one above. This would look a little messy, so have each case call a function to do it's work.

Hope this helps a bit :+)
Last edited on
1
2
3
bool romanType::verifyInput(const string &roman){
   return roman.find_first_not_of( "IVXLCDM" ) == std::string::npos;
}


If your container is not an string, you could use `std::find_if_not()' and a `member()' function (possible implemented with `find() )


@TheIdeasMan: those should be single quotes you can't make that switch.
It should be on single characters, not strings.
Last edited on
@ne555

Very good that is much easier, my poor excuse is probable hypo-caffeination :<D.

At least by mentioning my dislike, it prompted you to provide a much better solution.
Topic archived. No new replies allowed.