0

just started off with c++, and stackoverflow for that matter. any and help infinitely appreciated, apologies in advance if i ask something super dumb

I'm making a program to solve a problem. How many 8 digit numbers are divisible by 18 and are only comprised of the digits 1, 2 and 3. I can generate numbers, but when calling a function i made to use modulus to determine whether they're divisible by 18 or not, the function gives me the error in the title. my code is as follows:

main.cpp

#include <iostream>
#include "functions.h"
using namespace std;

int main()
{
    functions f();
    for(int a = 1; a<4; a++){
    for(int b = 1; b<4; b++){
    for(int c = 1; c<4; c++){
    for(int d = 1; d<4; d++){
    for(int e = 1; e<4; e++){
    for(int f = 1; f<4; f++){
    for(int g = 1; g<4; g++){
    for(int h = 1; h<4; h++){
        int number = 10000000*a + 1000000*b + 100000*c + 10000*d + 1000*e + 100*f + 10*g + h; //generates 8 digit numbers, only using the digits 1 2 and 3
        cout << number << endl; //prints numbers
        int y = 10; //to test this bloody function
        cout << f.modu18()(y); //returns 0 or 1 from func
}}}}}}}}}

functions.h

#ifndef FUNCTIONS_H
#define FUNCTIONS_H
#include <iostream>

using namespace std;

class functions
{
    public:
        functions();
        string modu18(int x);
    protected:
    private:
};

#endif

functions.cpp

#include "functions.h"
#include <iostream>

using namespace std;

functions::functions(){

    cout << "Functions initialised!" << endl; //to see if this thing is actually loading

}

string functions::modu18(int x){ //this is checking whether the number is divisible by 18
    if(x % 18 == 0){
        return 0;
    }else{
        return 1;
    };
} //btw, using multiple files becuase i want to learn how to make this work for the future

The exact error returned when compiling is

request for member 'modu18' in 'f', which is of non-class type 'int'

I have no clue why this is saying this, all my data types are correct, for the data and the function types. send help pls Many thanks.

Konzo
  • 29
  • 5
  • Why does `class functions` exist in the first place? You can make `modu18` a global free function as well. –  Nov 16 '18 at 22:56
  • I wanted to put the function in a separate file, so I made a new class in the project and voila. Is there a different way? – Konzo Nov 16 '18 at 23:00
  • Yes, do the same, but without a class. And search a C++ reference for the header to include when you want to use `std::string`. – juanchopanza Nov 16 '18 at 23:01
  • "all my data types are correct" -- are you sure about that? For starters, you are `return`ing an `int`eger from a function declared as `string ....()`. – CompuChip Nov 16 '18 at 23:05
  • I'll try this. Thanks! – Konzo Nov 16 '18 at 23:06
  • compuchimp, well, they were at one point. i was just trying anything i could to make it work, since nothing else i tried didnt. – Konzo Nov 16 '18 at 23:07

1 Answers1

0

In your function main there are two different f:

First one here

functions f();

is a variable of type functions or at least that is what you expect (see comments, the correct definition would be functions f;. As it is now, this would be the declaration of a function taking no arguments and returning an object of type functions).

The second one here:

for(int f = 1; f<4; f++){

is of type int.

The for loop is in a different scope than the where the first declaration is (each {} introduces a new scope) and therefore it is allowed to reuse identifiers for different objects.

If you refer to the doubly-used name, it will be looked up by certain rules and in the most common case the one in the most-inner scope will be used. Therefore here

cout << f.modu18()(y); //returns 0 or 1 from func

f is the loop counter of type int, not the f declare in the outer scope.

Use different variable names to solve this issue.

Additional stuff unrelated to error message:

  1. Your function modu18 is supposed to return a string, but all your return statements return integer literals which are of integer type and can not be automatically cast to std::string, or rather the implicit conversion will not do what you expect it to.

  2. You do not need classes to use multiple files. In a header file you can declare a free function with string modu18(int); and then define it in the implementation file with string modu18(int a) { ... }.

  3. Using using namespace std; is not good practice, as it will lead to very hard to understand errors down the line. Especially in header files it should never be used. Instead specify all names from the standard library fully with std::.

  • 1
    @KenziMarcel The first `f` is actually a function, not a "variable". See https://stackoverflow.com/questions/180172/default-constructor-with-empty-brackets. – juanchopanza Nov 16 '18 at 23:05
  • @juanchopanza Yes thanks for noticing. I keep missing that for some reason. –  Nov 16 '18 at 23:15