Форум программистов, компьютерный форум, киберфорум
С++ для начинающих
Войти
Регистрация
Восстановить пароль
Карта форума Темы раздела Блоги Сообщество Поиск Заказать работу  
 
 
Рейтинг 4.90/89: Рейтинг темы: голосов - 89, средняя оценка - 4.90
1 / 1 / 1
Регистрация: 08.04.2014
Сообщений: 31
1

Классы.Ключевое слово static - выдает ошибку "неразрешенный внешний символ"

09.04.2014, 00:39. Показов 16329. Ответов 23
Метки нет (Все метки)

Author24 — интернет-сервис помощи студентам
Всем доброго времени суток.
Изучаю С++ по Шпаку и по урокам на сайте
Кликните здесь для просмотра всего текста
cppstudio.com
, предварительно хорошо ознакомившись с ассемблером...
Со всеми темами прорываюсь вперед без особых затруднений, дошел до изучения классов, начали появляться вопросы, вот решил найти себе пристанище для ответов.
По первому же запросу в гугле попал сюда =)
Ну да ладно...вообщем плохо разобрался со статической переменной static, точней понимаю, что она создаётся один раз, содержит последнее, внесённое в неё значение... а дальше, работа с классами и оператором расширения области действия :: очень запутался...

На данный момент вот такая проблема.

Visual studio 2013 выдаёт такие ошибки.

Мои догадки:
-из-за того, что интерфейс и реализация в одном файле...
-из-за компилятора, вставляю стандартный код, который был приведён для примера, выдаёт такие же ошибки.


Ошибка 1 error LNK2001: неразрешенный внешний символ ""private: static int AB::a" (?a@AB@@0HA)" C:\Users\garjo\Documents\Visual Studio 2013\Projects\Проект68\Проект68\Исходный код.obj Проект68

Ошибка 2 error LNK2001: неразрешенный внешний символ ""private: static int AB::b" (?b@AB@@0HA)" C:\Users\garjo\Documents\Visual Studio 2013\Projects\Проект68\Проект68\Исходный код.obj Проект68


Ошибка 3 error LNK1120: неразрешенных внешних элементов: 2 C:\Users\garjo\Documents\Visual Studio 2013\Projects\Проект68\Debug\Проект68.exe Проект68
при компиляции этого кода
C++
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
#include <iostream>
 
using namespace std;
 
class AB //создаём класс 
{
private:
    static int a;
    static int b;
 
public:
    AB()
    {
        a = 1;
        b = 1;
        cout << "Тут сработал конструктор" << endl;//и здесь же их отобразим на экран
        cout << "a = " << a << endl;
        cout << "b = " << b << endl << endl;
    }
 
    void setAB()
    {
        cout << "Введите целое число а: ";
        cin >> a;
        cout << "Введите целое число b: ";
        cin >> b;
    }
 
    void getAB()
    {
        cout << "a = " << a << endl;
        cout << "b = " << b << endl << endl;
    }
 
    /*~AB() // это деструктор. не будем заставлять его чистить память, пусть просто покажет где он сработал
    {
        cout << "Тут сработал деструктор" << endl;
        system("pause");
 
    }*/
};
 
int main()
{
    setlocale(LC_ALL, "rus");
 
    AB obj1; //сработал конструктор
 
    obj1.getAB(); //для явной проверки
    obj1.setAB();   //присвоим новые значения переменным
    obj1.getAB();   //и выведем их на экран
 
    AB obj2;
    obj2.getAB;
    obj2.setAB;
    obj2.getAB;
 
    system("pause");
    return 0;
 
}
0
Programming
Эксперт
94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
09.04.2014, 00:39
Ответы с готовыми решениями:

Не могу запустить программку компилятор выдаёт ошибку error LNK2019: ссылка на неразрешенный внешний символ
Прошу прощения за глупые вопросы но я новичок в програмировании .Вот моя программка и копия ошибки...

Выдает ошибку "ссылка на неразрешенный внешний символ _main"
Помогите пожалуйста решить проблему. Выдает ошибку error LNK2019: ссылка на неразрешенный внешний...

Ссылка на неразрешенный внешний символ (классы)
Доброе время суток! Не накрученный код, вроде бы все хорошо, но компилятор выдает ошибку: :...

Классы и методы, error LNK2001: неразрешенный внешний символ
пожалуста, посмотрите код, и скажите почему вылетает данная ошибка? // lab.k.kurs.cpp:...

23
54 / 53 / 5
Регистрация: 14.08.2012
Сообщений: 252
09.04.2014, 00:47 2
Для статических переменных нужно делать разрешение символа, т.е. написать вне класса:

int AB::a;
int AB::b;

Т.к. по сути статические переменные не принадлежат классу.
Так что ваши догадки пока неверны)
1
18840 / 9839 / 2408
Регистрация: 30.01.2014
Сообщений: 17,280
09.04.2014, 00:59 3
Цитата Сообщение от AceOfSpades Посмотреть сообщение
Т.к. по сути статические переменные не принадлежат классу.
Они принадлежат классу, но не принадлежат объекту.

garjo_099,
А необходимость вынесения определения переменных точно такая же, как необходимость определения объявленных в классе функций. То есть семантически вот эти записи связаны:
C++
1
2
3
4
5
6
7
8
9
10
11
class A
{
public:
    void f(); // объявление
    static int a; // объявление
    static void fs(); // объявление
};
 
int A::a = 0; //определение
void A::f() {} //определение
void A::fs() {} //определение
1
5498 / 4893 / 831
Регистрация: 04.06.2011
Сообщений: 13,587
09.04.2014, 01:11 4
garjo_099, под поля класса, память, при объявлении класса, не выделяется. Память под них выделяется при создании объектов класса, но так как статические переменные класса не принадлежат объектам, то память под них необходимо выделить отдельно (определить эти переменные вне класса).
0
8 / 8 / 2
Регистрация: 21.11.2013
Сообщений: 22
09.04.2014, 01:17 5
статические классы члены и методы класса относяться к классу в целом, а не к отдельному объекту

статический член класса существует в единственном экземляре, независимо оттого, созданы ли объекты класса и сколько

статический метод класса можно вызвать, даже если нет ни одного экземпляра класса ( допустим у тебя в классе дата есть такой метод getCurrentDate но если он не статический то что бы допустим узнать текущию дату тебе нужно создать объект в мейне ну вот такие вещи и делают статикой что бы не создавать объект)

C++
1
cout << "Today is " << Date::getCurrentDate() << endl;
если не статикой то нужно в мейне создавать объект
зачем нам нужно объявлять переменные типа дата если мы просто хотим узнать текущую дату
C++
1
2
Date d;
cout << "Today is " << d.getCurrentDate() << endl;
0
54 / 53 / 5
Регистрация: 14.08.2012
Сообщений: 252
09.04.2014, 01:59 6
Цитата Сообщение от DrOffset Посмотреть сообщение
Они принадлежат классу, но не принадлежат объекту.
Не совсем так. Возможно я неправильно выразился.

Статические данные класса по сути - глобальные переменные с видимостью в namespace класса.
Статические члены данных не является частью объектов заданного типа класса; они отдельные объекты. В результате объявление статического члена данных не является определением. Элемент данных объявлен в области класса, но определение выполняется в области файла.
Как-то так.
0
18840 / 9839 / 2408
Регистрация: 30.01.2014
Сообщений: 17,280
09.04.2014, 08:24 7
Цитата Сообщение от AceOfSpades Посмотреть сообщение
Не совсем так.
Storage duration и принадлежность чему-либо в С++ понятия независимые. Если нечто объявлено внутри функции - оно принадлежит функции. Если нечто объявлено внутри namespace - оно принадлежит namespace. Если нечто объявлено внутри класса - оно принадлежит классу, в частности доступ к static полям все так же разрешается спецификаторами доступа. Так что мое определение вполне верное.

Цитата Сообщение от AceOfSpades Посмотреть сообщение
Статические члены данных не является частью объектов заданного типа класса
Именно об этом я и написал и про определение и объявление тоже.
0
1 / 1 / 1
Регистрация: 08.04.2014
Сообщений: 31
09.04.2014, 16:36  [ТС] 8
переделал код, и он показывает, что переменная в каждом экземпляре класса (при создании большого количества объектов класса) хранит последние внесённые в неё данные.
C++
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 <iostream>
 
using namespace std;
 
class AB //создаём класс 
{
private:
    static int a;
    static int b;
 
public:
    AB()
    {
        cout << "Тут сработал конструктор" << endl;//и здесь же их отобразим на экран
        cout << "a = " << a << endl;
        cout << "b = " << b << endl << endl;
    }
 
    void setAB()
    {
        cout << "Введите целое число а: ";
        cin >> a;
        cout << "Введите целое число b: ";
        cin >> b;
    }
 
    void getAB()
    {
        cout << "a = " << a << endl;
        cout << "b = " << b << endl << endl;
    }
 
    /*~AB() // это деструктор. не будем заставлять его чистить память, пусть просто покажет где он сработал
    {
        cout << "Тут сработал деструктор" << endl;
        system("pause");
 
    }*/
};
 
int AB::a;
int AB::b;
 
int main()
{
    setlocale(LC_ALL, "rus");
 
    AB obj1; //сработал конструктор
 
    obj1.getAB(); //для явной проверки
    obj1.setAB();   //присвоим новые значения переменным
    obj1.getAB();   //и выведем их на экран
 
    AB obj2;
    obj2.getAB();
    obj2.setAB();
    obj2.getAB();
 
    system("pause");
    return 0;
 
}
Добавлено через 3 минуты
anonymous_, ага спасибо, вроде немножко разтуманилось.

Добавлено через 4 минуты
И ещё вопрос. Из-за чего лучше объявлять определение за интерфейсом класса???
0
54 / 53 / 5
Регистрация: 14.08.2012
Сообщений: 252
09.04.2014, 16:44 9
Цитата Сообщение от garjo_099 Посмотреть сообщение
И ещё вопрос. Из-за чего лучше объявлять определение за интерфейсом класса???
Не просто за интерфейсом, а лучше в отдельном cpp файле. Почитайте про раздельную компиляцию. Когда есть h-файл и его реализация в cpp-файле можно конечному пользователю поставлять только интерфейс в h-файле и скомпилированный cpp-файл, т.е. не выдавать исходные коды.
0
1 / 1 / 1
Регистрация: 08.04.2014
Сообщений: 31
09.04.2014, 20:09  [ТС] 10
Подскажите алгоритм как реализовать, ввод даты допустим, через точку в формате дд.мм.гггг

Добавлено через 9 минут
Через разбор строки наверное будет самый простой способ...

Добавлено через 42 минуты
а точней преобразовать строку дд.мм.гггг в числа и разбить в структуру или по отдельным переменным без точки.
0
18840 / 9839 / 2408
Регистрация: 30.01.2014
Сообщений: 17,280
09.04.2014, 20:11 11
garjo_099, scanf такое может
0
1 / 1 / 1
Регистрация: 08.04.2014
Сообщений: 31
09.04.2014, 20:33  [ТС] 12
от примера не отказался бы =)))
0
18840 / 9839 / 2408
Регистрация: 30.01.2014
Сообщений: 17,280
09.04.2014, 21:12 13
Цитата Сообщение от garjo_099 Посмотреть сообщение
от примера не отказался бы =)))
C++
1
2
3
4
5
6
7
8
9
10
11
#include <cstdio>
 
int main()
{
    int d = 0, m = 0, y = 0;
    if(scanf("%2d.%2d.%4d", &d, &m, &y) == 3)
    {
        printf("%d.%d.%d\n", d, m, y);
    }
    return 0;
}
0
1 / 1 / 1
Регистрация: 08.04.2014
Сообщений: 31
10.04.2014, 01:34  [ТС] 14
Написал код, только сильно не пинайте и громко не смейтесь=)) программка чисто для практики, писал код собственными алгоритмами, построенные в моей голове на основе того, что знаю на данный момент, никуда не подглядывая. Вообщем цель перевести строку даты в целочисленные тип данных. Помогите найти ошибки, с функцией, что-то не так и с оператором gets в main функции, не запрашивает повторный ввод, код компилится но выдаёт ошибку.

C++
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
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
#include <iostream>
 
using namespace std;
 
bool preobrazStroki(char *); //прототип функции которая преобразует строку в символы
 
struct day
{//вообщем глобальные переменные для хранения отработаных результатов
    static char a, b;
};
struct mm
{
    static char a, b;
};
struct year
{
    static char a, b, c, d;
};
 
char day::a, day::b;
char mm::a, mm::b;
char year::a, year::b, year::c, year::d;
 
int main()
{
    setlocale(LC_ALL, "rus");
 
    char currentdate[11];//строка куда будем записывать дату
    bool stop = true;//переменная для условия выхода из цикла while
    //char *ptrcurrentdate = &currentdate[11];
    while (stop == true)
    {
        cout << "Введите дату в формате дд.мм.гггг" << endl;
 
        gets_s(currentdate);//считываем символы с клавиатуры в строку  п.с.и почему-то при повторном запуске цикла не запрашивает ввод данных
 
        char *ptrcurrentdate = &currentdate[11]; //так и не определился где лучше создать указатель вне цикла или внутри цикла...
        cout << ptrcurrentdate << endl;//для проверки, но выпуливает какой-то шлак(((
 
        if (currentdate[2] == '.' && currentdate[5] == '.')// первые условия правильности ввода даты
        {
            if (preobrazStroki(ptrcurrentdate))//если функция вернёт тру
            {
                int day1 = day::a - '0', day2 = day::b - '0', mm1 = mm::a - '0', mm2 = mm::b - '0';//конечные переменные с которымы
                //в будущем можно будет работать и вычислять количество дней с вашего дня рождения =))))
                int yy1 = year::a - '0', yy2 = year::b - '0', yy3 = year::c - '0', yy4 = year::d - '0';
                cout << day1 << day2 << "." << mm1 << mm2 << ".";//печать даты уже в формате int
                cout << yy1 << yy2 << yy3 << yy4 << endl;
            }
        }
        else
        {
            cout << "Неверный формат даты, вводите в таком формате дд.мм.гггг!\n";
            cout << "Если желаете продолжить нажмите 1, если хотите выйти, нажмите 0\n";//тут всё понятно я думаю
            cin >> stop;
 
        }
 
    }
 
 
    system("pause");
    return 0;
}
 
bool preobrazStroki(char *value)
{
    //day day1;
    //mm mm1;
    //year year1;
    
    while (*value != '\0')//пока указатель не будет указывать на asciiz
    {//собственно сама функция и с ней что-то не то.
        if (isdigit(*value))//если все if сработают функция вернёт true и дата запишется в глобальные переменные 
        {
            day::a = *value;
            value++;
        }
        else
        {
            cout << "neverniu format" << endl;
            break;//было задумано, если программа находит какой-то символ, а не цифру, то функция возвращает false
        }
 
            if (isdigit(*value))
            {
 
                day::b = *value;
                value += 2;
            }
            else
            {
                cout << "neverniu format" << endl;
                break;
            }
            if (isdigit(*value))
            {
 
                mm::a = *value;
                value++;
            }
            else
            {
                cout << "neverniu format" << endl;
                break;
            }
            if (isdigit(*value))
            {
                mm::b = *value;
                value += 2;
            }
            else
            {
                cout << "neverniu format" << endl;
                break;
            }
            if (isdigit(*value))
            {
 
                year::a = *value;
                value++;
            }
            else
            {
                cout << "neverniu format" << endl;
                break;
            }
            if (isdigit(*value))
            {
 
                year::b = *value;
                value++;
            }
            else
            {
                cout << "neverniu format" << endl;
                break;
            }
 
            if (isdigit(*value))
            {
            year::c = *value;
                value++;
            }
            else
            {
                cout << "neverniu format" << endl;
                break;
            }
    
            if (isdigit(*value))
            {
                year::d = *value;
                value++;
            }
            else
            {
            cout << "neverniu format" << endl;
            break;
            }
            return true;
    }
    return false;
}
0
5498 / 4893 / 831
Регистрация: 04.06.2011
Сообщений: 13,587
10.04.2014, 02:14 15
Цитата Сообщение от garjo_099 Посмотреть сообщение
не запрашивает повторный ввод
C++
1
(cin >> stop).get();
0
1 / 1 / 1
Регистрация: 08.04.2014
Сообщений: 31
10.04.2014, 10:54  [ТС] 16
Цитата Сообщение от alsav22 Посмотреть сообщение
Код C++
1
(cin >> stop).get();
Повторный ввод строки gets_s!
0
5498 / 4893 / 831
Регистрация: 04.06.2011
Сообщений: 13,587
10.04.2014, 11:00 17
Цитата Сообщение от garjo_099 Посмотреть сообщение
Повторный ввод строки gets_s!
И что?
0
1 / 1 / 1
Регистрация: 08.04.2014
Сообщений: 31
10.04.2014, 11:05  [ТС] 18
alsav22, ты вводишь дату, ввёл неправильно, цикл спрашивает ещё будете вводить или нет, если да то уже не срабатывает ввод даты, а опять же к этому месту выбора в цикле, скомпилируй код и просто посмотри
0
5498 / 4893 / 831
Регистрация: 04.06.2011
Сообщений: 13,587
10.04.2014, 11:42 19
Цитата Сообщение от garjo_099 Посмотреть сообщение
скомпилируй код и просто посмотри
Оно мне надо? Вопрос был такой:
Цитата Сообщение от garjo_099 Посмотреть сообщение
не запрашивает повторный ввод
Сейчас запрашивает?
Цитата Сообщение от garjo_099 Посмотреть сообщение
Повторный ввод строки gets_s!
0
1 / 1 / 1
Регистрация: 08.04.2014
Сообщений: 31
10.04.2014, 11:51  [ТС] 20
Да. Можно объяснить почему без добавления функции get() не работало. А с функцией, что? не подскажите?
0
10.04.2014, 11:51
IT_Exp
Эксперт
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
10.04.2014, 11:51
Помогаю со студенческими работами здесь

Помогите устранить ошибку: ссылка на неразрешенный внешний символ
Здравствуйте! Помогите бьет ошибку: error LNK2019: ссылка на неразрешенный внешний символ...

Исправить ошибку LNK2019: ссылка на неразрешенный внешний символ (InternetCheckConnection и WinAPI)
Создаю простенькое приложение на winapi с кнопкой и полем edit, по нажатию на которую происходит...

Компилятор выдает ошибку, LNK2019 ссылка на неразрешенный внешний символ
Программа не запускается, где-то ошибка не могу понять где. Помогите найти! Файлы из программы вот...

Не могу исправить ошибку средства Link: ссылка на неразрешенный внешний символ
Помогите, пожалуйста разобраться. Сам пытался понять, не смог. Главное, что, когда компилируешь...

Ссылка на неразрешенный внешний символ, неразрешенный внешний элемент
В программировании новичок, знакомство с подпрограммами. Помогите понять, в чем ошибка. Программа...

Шаблонные классы и ошибка линковки "Ссылка на неразрешенный внешний символ"
Здравствуйте Не первый раз сталкиваюсь с такой проблемой: допустим, хочу реализовать односвязный...

Есть проблема, при запуску программы выдают вот такую ошибку: ссылка на неразрешенный внешний символ "int
#include &quot;iostream&quot; using namespace std; int day, month, year; int GetMonthMax(int month); int...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
20
Ответ Создать тему
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2024, CyberForum.ru