Форум программистов «Весельчак У»
  *
Добро пожаловать, Гость. Пожалуйста, войдите или зарегистрируйтесь.
Вам не пришло письмо с кодом активации?

  • Рекомендуем проверить настройки временной зоны в вашем профиле (страница "Внешний вид форума", пункт "Часовой пояс:").
  • У нас больше нет рассылок. Если вам приходят письма от наших бывших рассылок mail.ru и subscribe.ru, то знайте, что это не мы рассылаем.
   Начало  
Наши сайты
Помощь Поиск Календарь Почта Войти Регистрация  
 
Страниц: [1] 2  Все   Вниз
  Печать  
Автор Тема: глюк?  (Прочитано 28339 раз)
0 Пользователей и 7 Гостей смотрят эту тему.
Алексей++
глобальный и пушистый
Глобальный модератор

ru
Offline Offline
Сообщений: 13


« : 06-07-2006 14:42 » 

случайно столкнулся с такой непоняткой:
(компилятор ошибку пропускает на ура)

Код:
	CString txt;
const char* c1;
const char* c2;

//тут всё нормально:
c1=(const char*)txt;

//а тут нипанятна :) (обратите внимание на лишний звёздочк)
c2=(const char*)*txt;

под микроскопом
Код:
	
118:      //тут всё нормально:
119:      c1=(const char*)txt;
00408082   lea         ecx,[ebp-14h]
00408085   call        CString::operator char const * (0040e81e)
0040808A   mov         dword ptr [ebp-18h],eax
120:
121:      //а тут нипанятна :) (обратите внимание на лишний звёздочк)
122:      c2=(const char*)*txt;
0040808D   lea         ecx,[ebp-14h]
00408090   call        CString::operator char const * (0040e81e)
00408095   movsx       ecx,byte ptr [eax]
00408098   mov         dword ptr [ebp-1Ch],ecx

в косячном случае добавлена команда расширения знакового бита у адреса txt - зачем?
Глюк?
Записан

alxmobile
Гость
« Ответ #1 : 06-07-2006 17:01 » 

2All
Интересно, что скажут знатоки синтаксиса С++.
Я думал, что (const char*)*txt == (const char*)(*txt)
Но оказывается, (const char*)*txt  == *(const char*)(txt)

2Алексей11532
Что касается команд процессора, то там расширяется не адрес, а байт по этому адресу.
Вот, смотри http://alpet.hotmail.ru/amdk6/amdopt.html
Записан
Алексей++
глобальный и пушистый
Глобальный модератор

ru
Offline Offline
Сообщений: 13


« Ответ #2 : 06-07-2006 18:05 » 

alxmobile, про то, ЧТО там расширяется, я в курсе Улыбаюсь  Команда расширяет знаковый бит при конвертации переменной

а вот - зачем это тут? глюк или нет?

>> Но оказывается, (const char*)*txt  == *(const char*)(txt)
 - точно, я проверил, а с чего бы это?? Улыбаюсь
« Последнее редактирование: 06-07-2006 18:10 от Алексей1153 » Записан

Scorp__)
Молодой специалист

ru
Offline Offline
Пол: Мужской

« Ответ #3 : 06-07-2006 18:14 » 

Лех, это связано с тем что, как справедливо заметил alxmobile:
Цитата
Но оказывается, (const char*)*txt  == *(const char*)(txt)

Получается, что ты берешь по адресу символ, так? А char - знаковый тип, поэтому компилятор и расширил знаковый бит. То есть это не глюк, а нормальная реакция, если конечно можно назвать ее нормальной после того как он твое желание вывернул наизнанку Улыбаюсь
Записан

- А Вы сами-то верите в привидения?
- Конечно, нет, - ответил лектор и медленно растаял в воздухе.
Алексей++
глобальный и пушистый
Глобальный модератор

ru
Offline Offline
Сообщений: 13


« Ответ #4 : 06-07-2006 18:23 » 

Scorp__), во первых , ЧТО он вывернул то? Улыбаюсь  Это же синтаксическая ошибка, насклько я понимаю - нельзя разыменовать txt , это не указатель.   И умножить на тип тоже низя Улыбаюсь)))

во вторых - но что там расширять-то? const char - это 1 байт
Записан

alxmobile
Гость
« Ответ #5 : 06-07-2006 18:52 » 

Алексей1153
Цитата
в косячном случае добавлена команда расширения знакового бита у адреса txt
Цитата
там расширяется не адрес, а байт по этому адресу
Цитата
про то, ЧТО там расширяется, я в курсе   Команда расширяет знаковый бит при конвертации переменной
Извини, просто формулировки невнятные.

А если по сути вопроса, то по-моему - баг.
У меня под VC60 повторяется.
Записан
alxmobile
Гость
« Ответ #6 : 06-07-2006 18:58 » 

Алексей1153
Цитата
Это же синтаксическая ошибка
Согласен.
Тем не менее, возможно, что txt - указетель. Я имею в виду, что в переменной txt физически хринится указеткль на экземпляр класса. Но тогда всё равно странно с точки зрения синтаксиса.
Записан
alxmobile
Гость
« Ответ #7 : 06-07-2006 19:14 » 

Так:
Упорядочиваю мысли и ложусь спать.

1. Операция разыменовывания имеет правое связывание, а это значит, что
(const char*)*txt  == (const char*)((txt))
Но это не соответствует коду

2.Согласно команд процессора, (const char*)*txt  == *(const char*)(txt)
Это выражение имеет тип char, но присваивается переменной char *
И это уже вторая ошибка

3. И еще есть вопрос - правомерно ли разыменовывать переменную экземпляра класса.
С одной стороны, в такой переменной фактически может хранится указатель.
А с другой - синтаксически недопустимо равноценно использовать переменную и указатель на нее.
Записан
Алексей++
глобальный и пушистый
Глобальный модератор

ru
Offline Offline
Сообщений: 13


« Ответ #8 : 06-07-2006 19:32 » 

пункт 3 - экземпляр невозможно разыменовать Улыбаюсь
Записан

alxmobile
Гость
« Ответ #9 : 06-07-2006 19:47 » 

Хех... уснуть не смог. Вот, полюбуйтесь:
Код:
int main(int argc, char* argv[])
{
  CString txt;
  CString *txt_ptr = new CString;
const char* str;
  char chr;

  str = (const char*)txt; //тут всё нормально, txt типа CString
 
  str = (const char*)*txt_ptr;  // Тоже все Ок, но txt_ptr типа CString*, и отличий в коде нет

  str = (const char*)*txt;  // Так делать не имеем права

  str = (const char*)(*txt);  // Конструкция соответствует предыдущей с точки зрения и синтаксиса и кода CPU

                            // А вот так мы читаем первый символ строки
  chr = *((const char*)txt);  // И команда movsx отсутствует

  return 0;
}
Код:
14:     str = (const char*)txt; //тут всё нормально, txt типа CString
00401087   lea         ecx,[ebp-10h]
0040108A   call        CString::operator char const * (00401386)
0040108F   mov         dword ptr [ebp-18h],eax
15:
16:     str = (const char*)*txt_ptr;  // Тоже все Ок, но txt_ptr типа CString*, и отличий в коде нет
00401092   mov         ecx,dword ptr [ebp-14h]
00401095   call        CString::operator char const * (00401386)
0040109A   mov         dword ptr [ebp-18h],eax
17:
18:     str = (const char*)*txt;  // Так делать не имеем права
0040109D   lea         ecx,[ebp-10h]
004010A0   call        CString::operator char const * (00401386)
004010A5   movsx       edx,byte ptr [eax]
004010A8   mov         dword ptr [ebp-18h],edx
19:
20:     str = (const char*)(*txt);  // Конструкция соответствует предыдущей с точки зрения и синтаксиса и кода CPU
004010AB   lea         ecx,[ebp-10h]
004010AE   call        CString::operator char const * (00401386)
004010B3   movsx       eax,byte ptr [eax]
004010B6   mov         dword ptr [ebp-18h],eax
21:
22:                                 // А вот так мы читаем первый символ строки
23:     chr = *((const char*)txt);  // И команда movsx отсутствует
004010B9   lea         ecx,[ebp-10h]
004010BC   call        CString::operator char const * (00401386)
004010C1   mov         cl,byte ptr [eax]
004010C3   mov         byte ptr [ebp-1Ch],cl
24:
25:     return 0;
Всё, на этот раз точно буду спать Улыбаюсь
Записан
Scorp__)
Молодой специалист

ru
Offline Offline
Пол: Мужской

« Ответ #10 : 07-07-2006 08:17 » 

Алексей1153, я и не спорю, что это синтаксическая ошибка Улыбаюсь

Но получается, что первым действием мы преобразовали тип переменной txt из CString в *CString вот так: ((const char*)txt). Вторым действием над полученным указателем (с точки зрения компилятора уже указателем) проводим разыменование *((const char*)txt). То есть получаем char - знаковый символ. Теперь полученный символ компилятору предлагается записать в char *c2. В этом месте он почему-то решил не проявлять принципиальность, а сказать: "Ну в конце концов указатель - это двойное слово, а кто я такой, чтобы мешать записать байт в двойное слово? Вот только знак надо бы сохранить" Улыбаюсь

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

А про вывернутое наизнанку желание. Если не считать это опечаткой, то можно предположить, что программист хотел этими строчками
Код:
const char* c2;		//тут всё нормально:	
c1=(const char*)txt;
//а тут нипанятна :) (обратите внимание на лишний звёздочк)
c2=(const char*)*txt;

добиться такого результата  Внимание! Говорит и показывает...:
Разыменовать txt, преобразовать значение в указатель на строку (как если бы txt был на самом деле массивом указателей на строки) и сохранить полученное значение в указателе на строку с2. Если бы компилятор поставил действия в таком порядке, то он тут же обнаружил бы попытку разыменования переменной txt и сказал бы что это недопустимо. Но он почему-то решил пойти своим путем  Улыбаюсь
Записан

- А Вы сами-то верите в привидения?
- Конечно, нет, - ответил лектор и медленно растаял в воздухе.
alxmobile
Гость
« Ответ #11 : 07-07-2006 11:35 » 

Цитата
В этом месте он почему-то решил не проявлять принципиальность, а сказать: "Ну в конце концов указатель - это двойное слово, а кто я такой, чтобы мешать записать байт в двойное слово? Вот только знак надо бы сохранить"
Точно:
Код:
32:     str = (char*)chr;
00401028   movsx       eax,byte ptr [ebp-8]
0040102C   mov         dword ptr [ebp-4],eax
Цитата
но видимо он был так поражен первыми, что подумал: "Наверное он знает, что делает!!  ""
Цитата
Но он почему-то решил пойти своим путем
Отлично Как человек, прям...
Записан
Alf
Гость
« Ответ #12 : 07-07-2006 13:41 » 

случайно столкнулся с такой непоняткой:
(компилятор ошибку пропускает на ура)

Подобные плохо предсказуемые случаи встречаются сплошь и рядом при использовании приведения типов в старом стиле С. Используй лучше стиль С++, его как раз во избежание подобных непоняток и ввели.

P.S. Кстати, недавно пришла посылка из "Озона", книга С. Дьюхэрста "Скользкие места С++. Как избежать проблем при проектировании и компиляции ваших программ", сейчас читаю ее, как на работе свободная минутка выпадет. Раздел 40,"Приведения в старом стиле", как раз и начинается предостережением: "Не пользуйтесь приведениями в старом стиле". Полагаю, этим советом не стоит пренебрегать.
Записан
LP
Помогающий

ru
Offline Offline

« Ответ #13 : 07-07-2006 14:43 » 

Я не читал все, что выше, извините если повторюсь, но это не баг.
Инструкция
Код:
*txt;
вполне законна, т.к. здесь срабатывает перегруженный оператор CString::operator const char*().
Записан

Если эта надпись уменьшается, значит ваш монитор уносят
Алексей++
глобальный и пушистый
Глобальный модератор

ru
Offline Offline
Сообщений: 13


« Ответ #14 : 07-07-2006 15:01 » 

Scorp__), ты ошибаешься:

>> что первым действием мы преобразовали тип переменной txt из CString в *CString вот так:
>> ((const char*)txt).

я не приводил к указателю на CString, но использовал оператор класса CString
  operator LPCTSTR ( ) const;
 - я и не думал про приведение к указателю, просто ошибся и напечатал лишний астериск Улыбаюсь

>>А про вывернутое наизнанку желание. Если не считать это опечаткой, то можно предположить,
>> что программист хотел этими строчками
 - вот-вот , очепяталси я просто Улыбаюсь


Alf,
>>Подобные плохо предсказуемые случаи встречаются сплошь и рядом при использовании
>> приведения типов в старом стиле С. Используй лучше стиль С++, его как раз во избежание
>> подобных непоняток и ввели.

- я не пользовался стилями, я их просто не знаю... А где эту книгу мона скачать?
Записан

Алексей++
глобальный и пушистый
Глобальный модератор

ru
Offline Offline
Сообщений: 13


« Ответ #15 : 07-07-2006 15:02 » 

LP, непонятно, а как это он так срабатывает? тип ведь не указан
Записан

Scorp__)
Молодой специалист

ru
Offline Offline
Пол: Мужской

« Ответ #16 : 07-07-2006 15:25 » 

Алексей1153, да я же и не утверждаю, что ты это специально сделал Улыбаюсь Я просто разбираю действия компилятора, который вообще не знает ошибся ты, или это такая хитрая-прехитрая задумка. И пытаюсь ответить на вопрос: "откуда там появился movsx?". Вполне возможно, что и в моих рассуждениях кроется какая-то ошибка, даже точно Улыбаюсь потому что к указателю не типа CString*, а к указателю char*. Но сути это не меняет, как мне кажется Улыбаюсь

Кстати, в каком файле реализация CString? Или хотя бы объявление? Посмотреть на этот оператор Улыбаюсь
Записан

- А Вы сами-то верите в привидения?
- Конечно, нет, - ответил лектор и медленно растаял в воздухе.
LP
Помогающий

ru
Offline Offline

« Ответ #17 : 07-07-2006 16:26 » 

Инструкция *txt означает применение встроенного глобального оператора разыменования operator*(char*);, т.е. что-то вроде
Код:
built-in::operator(txt); //*txt
Здесь и срабатывает оператор преобразования, собственно, для этого-то он и предназначен.
Вот аналогичный код.
Код:
class A
{
public:
operator const char*()
{
return 0;
}
};

int main()
{
A txt;
*txt;//компилируется
return 0;
}

Это можно видеть если в Debug'e протрассировать программу по F11. Улыбаюсь
В Release компилятор оптимизирует и вызова оператора преобразования не видно.
« Последнее редактирование: 06-12-2007 19:01 от Алексей1153++ » Записан

Если эта надпись уменьшается, значит ваш монитор уносят
alxmobile
Гость
« Ответ #18 : 07-07-2006 18:56 » 

LP
Цитата
Инструкция *txt означает применение встроенного глобального оператора разыменования operator*(char*)
Весьма занимательно! Ну хорошо, пусть так. Тогда стается еще вопрос.
Выражение (const char*)*txt  имеет тип (char). Почему тогда компилятор молча присваивает его указателю с типом (char*)?
Записан
LP
Помогающий

ru
Offline Offline

« Ответ #19 : 07-07-2006 19:28 » 

Выражение (const char*)*txt  имеет тип char*, а не char.
Тип char имеет выражение (*txt) и представляет собой первый символ строки, хранящейся в CString, а уже операция (const char*) преобразует char в char*, - static_cast такое бы не пропустил. Улыбаюсь
Записан

Если эта надпись уменьшается, значит ваш монитор уносят
alxmobile
Гость
« Ответ #20 : 07-07-2006 20:02 » 

Тогда осталось для нас, неграмотных, расставить все точки на i:
Я пройдусь по порядку. Поправьте меня, если ошибусь.

1. Конструкцию *txt компилятор правильно воспринимает, как разыменовывание указателя. Так как txt указателем не является, то происходит неявное приведение типа, согласно определенных операторов класса.
2. Так как имеется только один такой оператор, а именно (char*), то выражение *txt принимает значение первого символа в буфере txt.
3. А теперь мы сами себе делаем подлянку через приведение символа к типу (char*).

Таким образом, имеет место две ошибки:
1. Не было учтено неявное приведение типа.
2. Использовалось приведение в старом стиле.

Спасибо, LP. Кажется, теперь все понятно.
Записан
Scorp__)
Молодой специалист

ru
Offline Offline
Пол: Мужской

« Ответ #21 : 07-07-2006 20:13 » 

Вот блин, пока писал, уже все за меня разобрали. Ладно оставлю пост для истории Улыбаюсь

Дизассемблер как мы помним говорит:
Код:
122:      c2=(const char*)*txt;
0040808D   lea         ecx,[ebp-14h]
00408090   call        CString::operator char const * (0040e81e)
00408095   movsx       ecx,byte ptr [eax]
00408098   mov         dword ptr [ebp-1Ch],ecx

То есть после разыменования достаем байт, этот байт затем расширяем до указателя. Хотя действительно, если первые две с половиной команды - разыменование (получаем адрес массива, достаем первый байт), а вторая половина третьей команды - преобразование типа, которое было явно указано и четвертая - присваивание, то получаем, что просили.
А именно (const char*)(*txt). Пожалуй в мои рассуждения действительно вкралась ошибка. Вот только странно, что при переписывании байта в двойное слово сохраняется знак. Что компилятор решил, что у нас и отрицательная область памяти есть? Или что это индекс? Вот этот момент тогда остается непонятным.
Записан

- А Вы сами-то верите в привидения?
- Конечно, нет, - ответил лектор и медленно растаял в воздухе.
Alf
Гость
« Ответ #22 : 07-07-2006 20:23 » new

А где эту книгу мона скачать?

Возможно, что еще нигде низя, она 2006 года издания, только вышла. Я купил ее в "Озоне" в бумажном виде.

Мой коллега попросил ее на выходные отсканить, но ниасилил. Она странного формата, в развернутом виде больше формата А4, в сканер не влазит. А по одной страничке сканить парень спекся быстро, там прилично, 264 страницы. Так что или раскошеливайся на 159р., или жди, может, у кого другого терпения больше окажется...
Записан
Алексей++
глобальный и пушистый
Глобальный модератор

ru
Offline Offline
Сообщений: 13


« Ответ #23 : 07-07-2006 20:27 » 

Alf, ясно Улыбаюсь
Может в "Питере" появится

Кстати, насчёт раскошеливайся - так её заказать можно? Где?
« Последнее редактирование: 07-07-2006 20:31 от Алексей1153 » Записан

Olegator
Команда клуба

ru
Offline Offline
Пол: Мужской

« Ответ #24 : 07-07-2006 21:01 » 

Кстати, насчёт раскошеливайся - так её заказать можно? Где?
Я купил ее в "Озоне" в бумажном виде.
http://www.ozon.ru/context/detail/id/2631001/
Записан
Алексей++
глобальный и пушистый
Глобальный модератор

ru
Offline Offline
Сообщений: 13


« Ответ #25 : 07-07-2006 21:07 » 

пасиба, посмотрю
Записан

Джон
просто
Администратор

de
Offline Offline
Пол: Мужской

« Ответ #26 : 07-07-2006 23:57 » 

Во намутили! Мужики, вы эт серьёзно? Жаль я раньше не заметил. А посему приношу извинения, что своевременно не внёс ясность. А в чём собственно говоря ошибка? Что тут непонятно? "Как вы яхту назовёте, так она и поплывёт" (с) Преобразование типов является сложнейшей задачей современной магии Ага А уж тем более с константными указателями.

Дело в том, что в начале вызывается оператор ОБЪЕКТА CString (НЕСТАНДАРТНОГО ТИПА ДАННЫХ С++!!!)
Код:
CString::operator LPCTSTR() const { return m_pchData; }

Поэтому ваще нет необходимости в кастинге. Можно просто записать:

c1 = txt;

Это вообще идеально - вы предоставляете объекту САМОМУ выбрать наиболее подходящий кастинг (а иначе начерта он нужен этот объект со всеми его свойствами?). В этом случае вы УЖЕ получите указатель на const char*.

Но вам этого мало, вам хочется поиздеваться и следует ещё один кастинг в const char*. Компилятор не понимает, что же вы от него хотите, но делает. Он обязан подчиняться.

Таким образом можно записать (я использую для наглядности переменные из Лёшкиного примера):

c2=(const char*)c1;

Тут всё в порядке? Или как? Ага Или привычней записать:

c2=c1;

Не ну можно конечно записать, так, для уверенности:

c2=(const char*)(const char*)(const char*)(const char*)c1;

чтоб, значит, железно было. Ага Компилятор и на это не обидится.

И, наконец, что же означает таинственная запись c2=(const char*)*c1; ? Уже все догадались? Для тех кто не догадался подсказка:

c2=(const char*)c1[0];

Конечно! Кастинг в const char* того, что лежит по указателю с1 - просто первый байт.
Может не все знают, но в С++ можно записать первый элемент массива как c1[0], так  и *с1. В случае с CString это будет первый байт мембера LPTSTR m_pchData. Причём даже не произойдёт обрезания данных, о чём бы неугомонный компилятор предупредил. Вы "расширяете" переменную с 8 до 32 (размер указателя на 32-битных системах) бит.
Чтож ему жаловаться? На какую ошибку? Синтактическую?

И всё! "Не далее, не более" (с) Ну а ответственность за суразность происходяшего лежит целиком на программере. Компилятор не должен, не обязан это проверять.
А может программер ДЕЙСТВИТЕЛЬНО хранит в первом байте указатель на некий массив символов? Тогда запись:

c2=(const char*)*c1;

не только, НЕ ошибочна, но и единственно верная!

Желаю всем приятных сновидений. Ага

ps У меня сейчас почти два часа ночи, температура 27 по Цельсию, влажность 72% и шуток я уже не понимаю. Это на тот случай, если это хорошо продуманный прикол.
« Последнее редактирование: 08-07-2006 00:01 от Джон » Записан

Я вам что? Дурак? По выходным и праздникам на работе работать. По выходным и праздникам я работаю дома.
"Just because the language allows you to do something does not mean that it’s the correct thing to do." Trey Nash
"Physics is like sex: sure, it may give some practical results, but that's not why we do it." Richard P. Feynman
"All science is either physics or stamp collecting." Ernest Rutherford
"Wer will, findet Wege, wer nicht will, findet Gründe."
Джон
просто
Администратор

de
Offline Offline
Пол: Мужской

« Ответ #27 : 08-07-2006 00:11 » 

Альф, просто так, совет (шёпотом). С цифровой камерой книжки "сканятся" на порядок быстрей. Камера (можно, например, отдолжить на время), штатив (ну или струбцина, тиски и тд, чтобы закрепить камеру), кусок чистого стекла - и размер (формат) книги уже не имеет значения. Ну конечно об освещении нужно позаботиться. А уж когда руку набьёшь - побыстрей промышленных сканеров для книжек будет. У тех много времени уходит на перелистывание (осторожничают), но до человеческих пальчиков им ещё далеко.
Записан

Я вам что? Дурак? По выходным и праздникам на работе работать. По выходным и праздникам я работаю дома.
"Just because the language allows you to do something does not mean that it’s the correct thing to do." Trey Nash
"Physics is like sex: sure, it may give some practical results, but that's not why we do it." Richard P. Feynman
"All science is either physics or stamp collecting." Ernest Rutherford
"Wer will, findet Wege, wer nicht will, findet Gründe."
Алексей++
глобальный и пушистый
Глобальный модератор

ru
Offline Offline
Сообщений: 13


« Ответ #28 : 08-07-2006 04:35 » 

Джон, нет, это не прикол был Улыбаюсь

но про то, что CString в случае *txt воспринимается как (&txt)[] или (txt.GetBuffer())[0]  не знал Улыбаюсь
Записан

Джон
просто
Администратор

de
Offline Offline
Пол: Мужской

« Ответ #29 : 08-07-2006 07:25 » 

Ок - насчёт прикола. Лёш, в данном КОНКРЕТНОМ случае *txt НЕ воспринимается как (&txt)[], тк слева от = у тебя стоит тип const char*, поэтому сначала будет кастинг, а уж потом *. Оператор кастинга возвращает указатель на переменную-член m_pchData, поэтому в данноом КОНКРЕТНОМ случае, это эквивалентно m_pchData[0].
В самом общем случае  *txt будет означать доступ к объекту находящемуся по адресу *txt. Попробую объяснить подробней.

Оператор * перед указателем означает, что ты хочешь получить дотсуп к самому объекту.

Например у тебя есть два указателя на объекты (те же CString):

CString *pstSrc;

CString *pstTarg;

Тогда операция pstTarg = pstSrc; приведёт к тому, что у тебя скопируется указатель. Проще говоря pstTarg будет показывать на тот же объект, что и pstSrc.
Для создания копии объекта необходимо вызвать оператор присваивания объекта ( типа oprator=(const &) ), запись выглядит след. образом - *pstTarg = *pstSrc; Причём заметь, в этом случае осуществляется не доступ к первому байту внутреннего буфера (те не pstSrc->GetAt(0)), а к всему объекту.
Другой пример, при передачи указателя в ф-ю

void Foo(int *pnSrc)
{
     int nTarg = *pnSrc; // копируем объект (НЕ УКАЗАТЕЛЬ) по адресу pnSrc в локальную переменную nTarg int nTarg = pnSrc; - неправильно в этом случае

    ....
}


void Foo(int *pnTarg)
{
     int nSrx = .... // вычисления ...
     ....
     
     *pnTarg = nTarg; // копируем результаты вычислений в объект по адресу pnSrc
}

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

int X[9];

int *pCnt = X;

while(!bStop)
{
     int nNextPos = F1(*pCnt);
     pCnt+=nNextPos;

     bStop = ...

И тд

Или например, использовать в случаях, за которые я люблю С++:

char *FindPosOf(char *pStr, char chNeed)
{
   char *pPos = pStr;
   while((*pPos!='\0')&&(*pPos++!=chNeed));
   return pPos;
}

   char chNeed = 'D';
   const char pszSrc [] = "ABCDEFGH";
   char *p = FindPosOf(pszSrc, chNeed);
   TRACE1("%s\n",p);


ЭТо только пример!!! Очень рекомендуется НЕ исползовать подобные записи. В больших проектах и при интимной работе их использование категорически запрещается!!!

Если немного сумбурно, или непонятно - попробую объяснить на свежую голову. А то по этой духоте и жаре пару часов сна означают вообще ничего.
« Последнее редактирование: 06-12-2007 19:11 от Алексей1153++ » Записан

Я вам что? Дурак? По выходным и праздникам на работе работать. По выходным и праздникам я работаю дома.
"Just because the language allows you to do something does not mean that it’s the correct thing to do." Trey Nash
"Physics is like sex: sure, it may give some practical results, but that's not why we do it." Richard P. Feynman
"All science is either physics or stamp collecting." Ernest Rutherford
"Wer will, findet Wege, wer nicht will, findet Gründe."
Страниц: [1] 2  Все   Вверх
  Печать  
 

Powered by SMF 1.1.21 | SMF © 2015, Simple Machines