Форум программистов, компьютерный форум, киберфорум
Наши страницы
С++ для начинающих
Войти
Регистрация
Восстановить пароль
 
Рейтинг 4.75/4: Рейтинг темы: голосов - 4, средняя оценка - 4.75
perevezenzev
2 / 2 / 1
Регистрация: 30.01.2013
Сообщений: 129
1

Массивы указателей и ошибка Access violation reading location

17.05.2015, 19:16. Просмотров 742. Ответов 19
Метки нет (Все метки)

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
#include "stdafx.h"
#include <iostream>
using namespace std;
 
 
class Number
{
public:
    int x;
    int calc(Number* start, Number* end)
    {
        Number* ptr = this; 
        int sum = 0;
        while (ptr != end)
        {
            sum += ptr->x;
            ptr++;
        }
        return sum-this->x;
    }
};
 
void main()
{
    Number* array[10];
    array[4]->calc(array[0], array[9]);
    system("pause");
}
Unhandled exception at 0x013C3084 in proj_1.exe: 0xC0000005: Access violation reading location 0xCCCCCCCC.
как я понял компилятор выходит за предел списка и выдает это исключение, как исправить мне этот код?
0
Similar
Эксперт
41792 / 34177 / 6122
Регистрация: 12.04.2006
Сообщений: 57,940
17.05.2015, 19:16
Ответы с готовыми решениями:

ошибка Access violation reading location 0x00000066
Ошибка : Unhandled exception at 0x100e14cf (msvcr100d.dll) in 3.4.exe:...

Ошибка: Unhandled exception at 0x772115de in TimeShift.exe: 0xC0000005: Access violation reading location 0x00041000.
всем привет! При использовании двумерного массива постоянно появляется ошибка...

Access violation reading location
Помогите пожалуйста! Создаю программу, которая ведет учет данных. В бинарный...

Access violation reading location
добрый вечер , что может означать ошибка ? &quot;Exception thrown at 0x00B427CD in...

access violation reading location
access violation reading location такая проблема если вести информацию про...

19
Perfilov
264 / 164 / 56
Регистрация: 25.02.2015
Сообщений: 435
17.05.2015, 19:23 2
Number* array[10]; - массив указателей. все они указывают неизвестно куда, поэтому любое обращение к объекту через любой указатель этого массива - это ошибка. надо, чтобы указатели указывали на реальные объекты.
если вы сделаете так, то проблем быть не должно:
C++
1
2
Number array[10];
array[4].calc(&array[0], &array[9]);
у намбер нужен конструктор,
который бы явно инициализировал x. не факт что дефолтный инициалиризует нулем
0
perevezenzev
2 / 2 / 1
Регистрация: 30.01.2013
Сообщений: 129
17.05.2015, 19:28  [ТС] 3
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
class Number
{
public:
    int x;
    Number(int _x)
    {
        x = _x;
    }
    int calc(Number* start, Number* end)
    {
        Number* ptr = this; 
        int sum = 0;
        while (ptr != end)
        {
            cout << "in while=" << ptr->x << endl;
            sum += ptr->x;
            ptr++;
        }
        return sum-this->x;
    }
};
 
void main()
{
    Number* array[10];
    for (int i = 0; i < 10; i++)
        array[i] = new Number(i);
 
    array[4]->calc(array[0], array[9]);
 
    system("pause");
}
Ошибку понял, "обновленная версия" не хочет перебрасывать указатель (см. стр 16) точнее перебрасывает но не корректно. На выводе:
in while=4
in while=-33686019
in while=-1414812757
in while=-1414812757
in while=0
in while=0
in while=918277603
in while=402693950
in while=13604048
in while=13604176
in while=0
in while=0
in while=4
in while=1
in while=146
in while=-33686019
in while=5
in while=-33686019
in while=-1414812757
in while=-1414812757
in while=0
in while=0
in while=918277603
in while=402693950
in while=13604112
in while=13604240
in while=0
in while=0
in while=4
in while=1
in while=147
in while=-33686019
in while=6
in while=-33686019
in while=-1414812757
in while=-1414812757
in while=0
in while=0
in while=918277603
in while=402693950
in while=13604176
in while=13604304
in while=0
in while=0
in while=4
in while=1
in while=148
in while=-33686019
in while=7
in while=-33686019
in while=-1414812757
in while=-1414812757
in while=0
in while=0
in while=918277603
in while=402693950
in while=13604240
in while=13604368
in while=0
in while=0
in while=4
in while=1
in while=149
in while=-33686019
in while=8
in while=-33686019
in while=-1414812757
in while=-1414812757
in while=0
in while=0
in while=918277603
in while=402693950
in while=13604304
in while=13604432
in while=0
in while=0
in while=4
in while=1
in while=150
in while=-33686019
хотя по идее итераций должно быть 6
0
Perfilov
264 / 164 / 56
Регистрация: 25.02.2015
Сообщений: 435
17.05.2015, 19:37 4
так происходит, потому что объекты у вас в памяти расположены не последовательно.
указатели в массиве - да. один за другим. но вот то, куда они указывает - эти объекты в памяти разбросаны, т.к.
в цикле при инициализации каждый вызов new не обязан выделять память сразу с куском, который был
выделен в предыдущей итерации.
0
perevezenzev
2 / 2 / 1
Регистрация: 30.01.2013
Сообщений: 129
18.05.2015, 19:54  [ТС] 5
Как мне обойти данное ограничение? Все мои попытки привели к неудаче.
0
Perfilov
264 / 164 / 56
Регистрация: 25.02.2015
Сообщений: 435
18.05.2015, 23:37 6
в моем первом сообщении тут есть вариант.
0
perevezenzev
2 / 2 / 1
Регистрация: 30.01.2013
Сообщений: 129
19.05.2015, 21:16  [ТС] 7
ну как я вас понял мне нужно передавать в функцию массив указателей
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
class Number
{
public:
    int x;
    Number(int _x)
    {
        x = _x;
    }
    int calc(Number* list[])
    {
        int sum = 0;
        Number* tmp = this;
        while (tmp != list[0])
        {
            cout << tmp->x << endl;
            tmp--;
        }
 
        return sum;
    }
};
 
void main()
{
    const int N = 10;
    Number* array[N];
    for (int i = 0; i < N; i++)
        array[i] = new Number(i);
 
    cout << array[4]->calc(array);
 
    system("pause");
}
но ничего не поменялось

Добавлено через 25 минут
По вашему коду, не получиться выделять память динамически
0
Perfilov
264 / 164 / 56
Регистрация: 25.02.2015
Сообщений: 435
19.05.2015, 23:41 8
конечно. там и не проедполагалось выделять ее динамически. если вам непременно надо что-то динамически выделить, то так и написали бы. для решения задачи в этом нет необходимости поэтому пример был самый простой. т.к. непонятно, что и как вам там надо динамически выделять, можете попробовать так:
C++
1
2
3
Number* array = new Number[10]; // чтобы компилилось, у Number должен быть конструктор без параметров
for (int i = 0; i < 10; i++)
  array[i] = Number(i);
в таком случае array будет указывать на диманически выделенный массив, в котором объекты Number рассположены последовательно и тогда уже можно инкрементить указатели, которые указывают на объекты этого массива.
1
perevezenzev
2 / 2 / 1
Регистрация: 30.01.2013
Сообщений: 129
20.05.2015, 22:39  [ТС] 9
Спасибо.
В дальнейшем у меня опять возникли трудности.
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
class Number
{
public:
    Number()
    {}
 
    Number(int _x)
    {
        x = _x;
    }
    virtual int calc(Number*, Number*) = 0;
    
    int x;
};
 
class Derivate : public Number
{
public:
    Derivate() : Number()
    {}
 
    Derivate(int _x) : Number(_x)
    {}
 
    int calc(Number* start, Number* end)
    {
        Number* ptr = this;
        int sum = 0;
        while (ptr != end)
        {
            sum += ptr->x;
            ptr++;
        }
        return sum - this->x;
    }
};
 
class Derivate1 : public Number
{
public:
    Derivate1() : Number()
    {}
 
    Derivate1(int _x) : Number(_x)
    {}
 
    int calc(Number* start, Number* end)
    {
        Number* ptr = this;
        int sum = 0;
        while (ptr != start)
        {
            sum += ptr->x;
            ptr--;
        }
        return sum - this->x;
    }
};
 
 
void main()
{
    const int N = 10;
    Number* array = new Number[N];
    for (int i = 0; i < N; i++)
        if (i % 2 == 0)
            array[i] = Derivate(i);
        else
            array[i] = Derivate1(i);
 
    cout << array[4].calc(&array[0], &array[N-1]);
 
    system("pause");
}
Возникает ошибка, ведь нельзя выделить память под абстрактный класс. Если сделать функцию calc не абстрактной, то всегда будет вызываться из базового класса. Как мне обойти данное ограничение?
0
Perfilov
264 / 164 / 56
Регистрация: 25.02.2015
Сообщений: 435
20.05.2015, 22:57 10
вы бы задание задание хоть описали со всем мракобесием вроде надо, чтобы обязательно динамически что-то выделялось. вот проблемы с массивами возникли из-за того, что вы попытались заложиться на то, что объекты у вас в памяти последовательно находятся. из этого появился код в методе calc. если на calc не наложено каких-то дуратских ограничений, то передавайте туда указатели на указатели. они то как раз последовательно рассположены. в этом случае вариант создания массива из сообщения #3 пройдет. надо будет только немного метод calc изменить. но это опять же закладка на то, что что-то как-то по хитрому в памяти рассположено, что ограничивает использование этого метода => само решение кривое
0
perevezenzev
2 / 2 / 1
Регистрация: 30.01.2013
Сообщений: 129
20.05.2015, 23:21  [ТС] 11
Задание такое: Сформировать массив объектов и для элемента массива с четным индексом сложить со всеми последующими эле-ментами, а для нечетными сложить со всеми предыдущими элементами.
0
Perfilov
264 / 164 / 56
Регистрация: 25.02.2015
Сообщений: 435
20.05.2015, 23:33 12
нигде не сказано, что что-то там должно быть динамически создано, что должны быть классы с виртуальными функциями и прочее, из-за чего вы нагенерили столько ненужного кода. вот можно сделать по простому и будет удовлетворять условию:
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
#include "stdafx.h"
#include <iostream>
using namespace std;
 
struct Number
{
public:
  Number()
  {
  }
 
  Number(int _x)
  {
    x = _x;
  }
    
  int x;
};
 
 
int calc(Number* arr, unsigned arrSize, unsigned index)
{
  // check index < arrSize - 1
  const bool odd = index % 2 ? true : false;
  Number* ptr = odd ? arr : &arr[index];
  Number* end = &arr[odd ? (index + 1) : arrSize];
  int res = 0;
  while (ptr != end)
  {
    res += ptr->x;
    ++ptr;
  }
  return res;
}
 
void main()
{
  const int N = 10;
  Number array[N];
  for (int i = 0; i < N; ++i)
  {
    array[i].x = 1;
  }
 
  std::cout << calc(array, N, 4) << std::endl;
  std::cout << calc(array, N, 1) << std::endl;
 
  //system("pause");
}
четность не четность и значения чисел подправте под себя если не так. смысл кода думаю понятен будет.
0
perevezenzev
2 / 2 / 1
Регистрация: 30.01.2013
Сообщений: 129
20.05.2015, 23:36  [ТС] 13
Я понимаю, что все просто когда делается так. Мне нужно сделать при помощи абстрактного класса, не так просто я себе усложняю жизнь.
Смысл в том, что я вызываю метод calc и он выполняться для четного и нечетного индекса по-разному.
0
Perfilov
264 / 164 / 56
Регистрация: 25.02.2015
Сообщений: 435
20.05.2015, 23:38 14
это троллинг чтоли? задание такое, но мне надо сделать по другому, не скажу как. помогите плиз.
0
perevezenzev
2 / 2 / 1
Регистрация: 30.01.2013
Сообщений: 129
20.05.2015, 23:42  [ТС] 15
Я скидывал свой код и просил помощи в исправлении ошибок, разве это для вас не нормальное задание?
0
Perfilov
264 / 164 / 56
Регистрация: 25.02.2015
Сообщений: 435
20.05.2015, 23:53 16
я вам подсказал первый раз как подправить. потом выяснилось, что вам нужно непременно что-то динамически создавать. ок, вроде тоже динамически что-то создалось. потом оказывается надо в массиве хранить указатели на динамически разные типы объектов. я как вроде не спрашивал зачем. потом выяснилось что то, что вы хотите замутить не решаемо в том виде, в котором оно представлено (закладка на рассоложение объектов). ладно, попробовал выяснить задание. в задании ничего не сказано про абстрактные классы, про то, что метод калькуляции должен находится в самом таком объекте. решение было представлено. оно оказалось не тем, т.к. вам оказывается нужны абстрактные классы. для чего - до выяснения этих обстоятельств мы не дошли. давайте я предположим, что вы сказали, что у объектов должна быть виртуальная функция и больше ничего не скажете. ну ок, я вам предложу завести какую-нибудь виртуальную функцию, которая ничего не делает и она даже не будет вызываться. потом вы скажете, для чего же она все-таки вам нужна и мне по новой что-то с этим придумывать надо будет ну и так до тех пор, пока из вас клещами не вытянется то, что вам надо. вместо этого нужно всего-то описать подробно TЗ
0
perevezenzev
2 / 2 / 1
Регистрация: 30.01.2013
Сообщений: 129
20.05.2015, 23:57  [ТС] 17
Я вас понял. Сформировать массив объектов (значение элемента и действие, реализуемое этим элементом) и для элемента массива с четным индексом сложить со всеми последующими эле-ментами, а для нечетными сложить со всеми предыдущими элементами.При выполнении задания использовать механизм наследования: опи-сать элемент массива как абстрактный базовый класс. Действие, реализуемое элементами массива, реализовать в виде виртуальных методов этого класса.
Надеюсь теперь не будет вопросов по ТЗ?
0
Perfilov
264 / 164 / 56
Регистрация: 25.02.2015
Сообщений: 435
21.05.2015, 00:08 18
вопросы остались. действие - это что? из предыдущего моего негодования это подпадает под виртуальную функцию, которая в частном случае ничего не делает, но можно сделать так, чтобы что-то бесполезное делала типа печатала на экран что-нибудь. если же действие - это складывание, то тут надо сидеть и думать, т.к. это несколько кривое использование виртуальных функций, какая-то виртуальная функция ради виртуальной функции без здравого смысла.
0
perevezenzev
2 / 2 / 1
Регистрация: 30.01.2013
Сообщений: 129
21.05.2015, 00:15  [ТС] 19
Да, к сожалению действие это сложение.
В сообщении #9 я привел примерный вид кода (архитектура такая), я просил помощи лишь в том что бы разобраться как работает арифметика указателей в данном случае (до сих пор не очень понял). Ну и если в этом случае нельзя использовать инкремент и декремент указателей как обойти данный механизм.
0
Perfilov
264 / 164 / 56
Регистрация: 25.02.2015
Сообщений: 435
21.05.2015, 00:21 20
мне пока видится такой вариант:
создается массив указателей на абстрактные классы.
далее в цикле под каждый указатель создается конкретный объект. и вот для вашей задумки в конструкторе
этому объекту нужно передать указатель на начало этого массива, размер массива и позицию создаваемого объекта в этом массиве. тогда в метод
калк ничего передавать не надо. в объекте будет хранится все, что нужно для прохода по массиву вперед или назад и это полная хрень. если это вас устраивает - сделайте. там не сложно. другие варианты в голову не приходят, может кто другой сообразит.
0
21.05.2015, 00:21
MoreAnswers
Эксперт
37091 / 29110 / 5898
Регистрация: 17.06.2006
Сообщений: 43,301
21.05.2015, 00:21

Access violation reading location
Уважаемые знатоки, подскажите пожалуйста в чем проблема или хотя бы типовые...

Помогите с ошибкой Access violation reading location 0x1ed1d9f8.
Не могу разобраться с VS.... У меня был хороший, проверенный проект, в котором...

Exception thrown at 0x77D75BCA (ntdll.dll): 0xC0000005: Access violation reading location 0x0000
Есть задача Есть решение Основное приложение: #include &quot;stdafx.h&quot;...


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

Или воспользуйтесь поиском по форуму:
20
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2018, vBulletin Solutions, Inc.
Рейтинг@Mail.ru