Форум программистов, компьютерный форум CyberForum.ru

Как правильно использовать friend для доступа к экземпляру класса - C++

Восстановить пароль Регистрация
 
Рейтинг: Рейтинг темы: голосов - 10, средняя оценка - 4.80
IcyWind
8 / 8 / 2
Регистрация: 19.09.2011
Сообщений: 268
21.12.2011, 23:45     Как правильно использовать friend для доступа к экземпляру класса #1
Доброго времени суток. Проблема - нужно из одного класса обратиться к методам экземпляра другого класса
знаю, что для этого нужно как-то использовать friend, а как - понять не могу

Скажем, есть класс index
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
class index
{
friend class indarray;  
    int *swapmas ;
    int size_;
public: 
    
    index(int n)
    {
        swapmas = new int(n);
        size_ = n;
        for(int i = 0; i<n; ++i)
        {
            swapmas[i] = n-i;
        }
    }
    int operator[](int i)
    {
        return swapmas[i];
    }
    int size()
    {
        return size_;
    }
};
(экземпляр класса назовём ind), к его методам нужно братиться в operator=
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
class indarray
{
    valarray &val;
    index &ind;
 
friend class valarray;
friend class index;
 
public:
    indarray(valarray &val_, index &ind_):val(val_), ind(ind_){}
 
    void operator = (valarray valar)
    {
        for(int i = 0; ind. //тут пишет, что члены недоступны. А очень хочется получить поле size_ через метод size
    }
};
Similar
Эксперт
41792 / 34177 / 6122
Регистрация: 12.04.2006
Сообщений: 57,940
21.12.2011, 23:45     Как правильно использовать friend для доступа к экземпляру класса
Посмотрите здесь:

C++ при перезагрузке оператора для класса не получается использовать имя переменной такое же,как в описании класса
Friend класса C++
C++ Как правильно использовать Указатели для массива (ошибки в программе)?
Как правильно перегрузить оператор для шаблона класса C++
C++ friend функции не имеют доступа к private элементам класса, почему?
После регистрации реклама в сообщениях будет скрыта и будут доступны все возможности форума.
DU
1477 / 1053 / 45
Регистрация: 05.12.2011
Сообщений: 2,279
21.12.2011, 23:49     Как правильно использовать friend для доступа к экземпляру класса #2
Если вы хотите из класса A обратиться к закрытым полям\метода класса B, то класс A должен быть другом класса B. т.е. в декларации класса B вы должны сказать, что класс A будет его другом.

C++
1
2
3
4
5
6
class B
{
  ...
  friend class A; // из-за этой строчки ко всем методам\членам класса B можно обращаться, находясь в классе A
  ...
};
У вас вроде так и сделано. Только еще "лишняя" дружба в другую сторону добавлена.
Какие у вас проблемы то?
IcyWind
8 / 8 / 2
Регистрация: 19.09.2011
Сообщений: 268
21.12.2011, 23:53  [ТС]     Как правильно использовать friend для доступа к экземпляру класса #3
C++
1
 index &ind;
не работает обращение ind.size()/ind.size_ и т.д. компилятор пишет, что "члены недоступны"
Причём, обращение index.size и подобные (то есть по имени класса, а не по его экземпляру) работают
DU
1477 / 1053 / 45
Регистрация: 05.12.2011
Сообщений: 2,279
22.12.2011, 00:01     Как правильно использовать friend для доступа к экземпляру класса #4
MS VS 8, все компилится. Может у вас что-то древнее и оно не понимает ключевого слова friend?
В чем пишите?

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
class Index
{
  friend class FriendOfIndex;
 
  int m_size;
 
public:
  int size() {}
};
 
class FriendOfIndex
{
  Index* m_index;
 
public:
  void F()
  {
    m_index->size(); // ok
    m_index->m_size; // ok;
  }
};
 
int main()
{
  Index index;
  FriendOfIndex friendOfIndex;
 
  return 0;
}
да и зачем вам эти френды? что мешает использовать публичные ф-ии класса?
IcyWind
8 / 8 / 2
Регистрация: 19.09.2011
Сообщений: 268
22.12.2011, 00:04  [ТС]     Как правильно использовать friend для доступа к экземпляру класса #5
Vs 2010

Добавлено через 33 секунды
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
#include "stdafx.h"
#include <iostream>
using namespace std;
 
 
class valarray
{
    int *mas;
    int size;
    
 
    /*~valarray()
    {
        delete[] mas;
    }*/
 
public:
    valarray(int n)
    {
        mas = new int[n];
        size =  n;
        for (int i = 0; i<size; ++i)
            mas[i] = rand();
    }
 
    void print()
    {
        //cout<<"\nМассив:\n";
        for(int i = 0; i<size; ++i)
            cout<<'['<<i<<"] = "<<mas[i]<<"\n";
    }
 
    int operator[](int n)
    {
        return mas[n];
    }
    indarray operator[](index t)
    {
        return indarray(*this, t);
    }
};
 
class indarray
{
    valarray &val;
    index &ind;
 
friend class valarray;
friend class index;
 
public:
    indarray(valarray &val_, index &ind_):val(val_), ind(ind_){}
 
    void operator = (valarray valar)
    {
        for(int i = 0; ind.size(); ++i) //тут пишет, что члены недоступны. А очень хочется получить поле size_ через метод size
    }
};
 
 
 
 
class index
{
friend class indarray;  
    int *swapmas ;
    int size_;
public: 
    
    index(int n)
    {
        swapmas = new int(n);
        size_ = n;
        for(int i = 0; i<n; ++i)
        {
            swapmas[i] = n-i;
        }
    }
    int operator[](int i)
    {
        return swapmas[i];
    }
    int size()
    {
        return size_;
    }
};
 
 
int _tmain(int argc, _TCHAR* argv[])
{
    setlocale(0, "Rus");
    valarray v(10),v1(10);
    index ind(10);
    cout<<"Массив v: \n";
    v.print();
//  v[ind] = v1; // v[ind[i]] = v1[i]
    return 0;
DU
1477 / 1053 / 45
Регистрация: 05.12.2011
Сообщений: 2,279
22.12.2011, 00:10     Как правильно использовать friend для доступа к экземпляру класса #6
C++
1
2
3
4
        void operator = (valarray valar)
        {
                for(int i = 0; ind.size(); ++i) //тут пишет, что члены недоступны. А очень хочется получить поле size_ через метод size
        }
Недоступен публичный метод size()? не настораживает?

как-то у вас все запущено. это вообще не компилится.
и вот почему не должно компилится:

у вас идут определения классов в такой порядке:
C++
1
2
3
class A { тут реализация методов };
class B {тут реализация методов };
class C {тут реализация методов };
Причем реализация методов сразу в классе. и вот в методах класса A вы обращаетесь к методам класса B. Но в классе A еще ничего не известно о классе B; Смотрите на строку 37 indarray определен ниже. в строке 37 компилятор еще ничего не знает об этом классе.

Вам поможет вот что:
C++
1
2
3
4
5
6
7
8
9
10
class A { тут объявления методов };
class B {тут объявления методов };
class C {тут объявления методов };
 
// А тут реалицация методов
A::xxx() {}
 
B::xxx() {}
 
C::xxx() {}
IcyWind
8 / 8 / 2
Регистрация: 19.09.2011
Сообщений: 268
22.12.2011, 00:14  [ТС]     Как правильно использовать friend для доступа к экземпляру класса #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
class index
{
friend class indarray;  
    int *swapmas ;
    int size_;
public: 
    
    index(int n)
    {
        swapmas = new int(n);
        size_ = n;
        for(int i = 0; i<n; ++i)
        {
            swapmas[i] = n-i;
        }
    }
    int operator[](int i)
    {
        return swapmas[i];
    }
    int size()
    {
        return size_;
    }
};
DU
1477 / 1053 / 45
Регистрация: 05.12.2011
Сообщений: 2,279
22.12.2011, 00:28     Как правильно использовать friend для доступа к экземпляру класса #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
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
#include "stdafx.h"
#include <iostream>
using namespace std;
 
class index
{
  int *swapmas;
  int size_;
public: 
  index(int n)
  {
    swapmas = new int(n);
    size_ = n;
    for(int i = 0; i<n; ++i)
    {
      swapmas[i] = n-i;
    }
  }
 
  int operator[](int i)
  {
    return swapmas[i];
  }
  int size()
  {
    return size_;
  }
};
 
 
class valarray; // из-за этого можно в декларации класса indarray использовать ссылки и указатели на valarray
 
 
class indarray
{
  valarray& val;
  index& ind;
 
public:
  indarray(valarray& val_, index& ind_);
  void operator = (const valarray& valar);
};
 
class valarray
{
  int *mas;
  int size;
        
public:
  valarray(int n);
  //~valarray();
 
  void print();
  int operator[](int n);
  indarray operator[](index t);
};
 
indarray::indarray(valarray &val_, index &ind_)
  : val(val_)
  , ind(ind_)
{
}
 
void indarray::operator = (const valarray& valar)
{
  for(int i = 0; ind.size(); ++i) //тут пишет, что члены недоступны. А очень хочется получить поле size_ через метод size
  {
  }
}
 
valarray::valarray(int n)
{
  mas = new int[n];
  size =  n;
  for (int i = 0; i<size; ++i)
    mas[i] = rand();
}
 
/*
valarray::~valarray()
{
  delete[] mas;
}
*/
 
void valarray::print()
{
  //cout<<"\nМассив:\n";
  for(int i = 0; i<size; ++i)
    cout<<'['<<i<<"] = "<<mas[i]<<"\n";
}
 
int valarray::operator[](int n)
{
  return mas[n];
}
 
indarray valarray::operator[](index t)
{
  return indarray(*this, t);
}
 
int _tmain(int argc, _TCHAR* argv[])
{
  setlocale(0, "Rus");
  valarray v(10),v1(10);
  index ind(10);
  cout<<"Массив v: \n";
  v.print();
  //v[ind] = v1; // v[ind[i]] = v1[i]
  return 0;
}
Корректность уже сами смотрите
IcyWind
8 / 8 / 2
Регистрация: 19.09.2011
Сообщений: 268
22.12.2011, 00:36  [ТС]     Как правильно использовать friend для доступа к экземпляру класса #9
То есть смысл в том, что нельзя использовать то, что не определено "выше"
DU
1477 / 1053 / 45
Регистрация: 05.12.2011
Сообщений: 2,279
22.12.2011, 00:39     Как правильно использовать friend для доступа к экземпляру класса #10
да. именно так. указатели и ссылки хранить или передавать в другие ф-ии можно, если выше есть хотябы декларация класса.
создавать экземпляры класса, обращаться к методам через указатель или ссылку, кастить к базовым классам, использовать sizeof(UnknownClass) - нельзя, если класс не определен выше.
MoreAnswers
Эксперт
37091 / 29110 / 5898
Регистрация: 17.06.2006
Сообщений: 43,301
22.12.2011, 00:40     Как правильно использовать friend для доступа к экземпляру класса
Еще ссылки по теме:

C++ Как правильно использовать классы? Как вывести значение класса на экран?
Передача свойства одного экземпляра класса другому экземпляру класса C++
C++ Не могу обратиться к Privat члену класса из ф-и Friend. Почему?

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

Или воспользуйтесь поиском по форуму:
IcyWind
8 / 8 / 2
Регистрация: 19.09.2011
Сообщений: 268
22.12.2011, 00:40  [ТС]     Как правильно использовать friend для доступа к экземпляру класса #11
Спасибо
Yandex
Объявления
22.12.2011, 00:40     Как правильно использовать friend для доступа к экземпляру класса
Ответ Создать тему
Опции темы

Текущее время: 03:14. Часовой пояс GMT +3.
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2016, vBulletin Solutions, Inc.
Рейтинг@Mail.ru