Указатели. В чЁм ошибка или где собака порылась?

Тема в разделе "WASM.BEGINNERS", создана пользователем vb_man, 27 ноя 2010.

  1. vb_man

    vb_man New Member

    Публикаций:
    0
    Регистрация:
    19 сен 2009
    Сообщения:
    24
    Парни, подскажите - где я не догоняю и как надо!
    Компелю в vc6.0 следующий код:
    Код (Text):
    1. #include <stdio.h>
    2. #include <stdlib.h>
    3.  
    4. char *S1()
    5. {
    6.     char *p="TEST_String";
    7.     return(p);
    8. }
    9. char *S2()
    10. {
    11.     char *p=NULL;
    12.     char a[12]="TEST_String";
    13.     p=a;
    14.     return(p);
    15. }
    16. ///////////
    17. void main()
    18. {
    19.     char *p=NULL;
    20.     char a[12]="TEST_String";
    21.     p=a;
    22.     printf("Result: %s\n",p);
    23.     p=S1();
    24.     printf("Result: %s\n",p);
    25.     p=S2();
    26.     printf("Result: %s\n",p);
    27. }
    В итоге:
    Result: TEST_String
    Result: TEST_String
    Result: TEST
    Ффункция S2()???
     
  2. Mika0x65

    Mika0x65 New Member

    Публикаций:
    0
    Регистрация:
    30 июл 2005
    Сообщения:
    1.384
    Строка улыбается :). Суть в том, что в первом случае "TEST_String" размещается в секции данных, а во втором -- в стеке, который нельзя использовать после выхода из ф-ии S2. Это все равно что вернуть адрес локальной переменной, которая действительна только в пределах ф-ии, в которой она объявлена. По выходу из этой ф-ии эту переменную использовать нельзя, даже если есть ее адрес.
     
  3. Mentor

    Mentor New Member

    Публикаций:
    0
    Регистрация:
    13 окт 2010
    Сообщения:
    67
    Функция S1:
    Строка размещена в сегменте данных, p - указатель на нее. После возврата из функции указатель валидный, данные валидные, всё ок

    Функция S2:
    Строка копируется в массив, размещенный на стеке. Возвращается указатель на локальную переменную. С фреймом после возврата может быть все что угодно, данные херятся

    main:
    данные копируются в локальную переменную, размещенную в стек-фрейме функции main. До возврата из main они валидные, можно использовать любые указатели на них, все ок.

    А что именно вы добиться пытаетесь? Локальную строковую переменную завести? Или вернуть строку из функции?
     
  4. vb_man

    vb_man New Member

    Публикаций:
    0
    Регистрация:
    19 сен 2009
    Сообщения:
    24
    Mika0x65 и Mentor спасибо! Вцелом понятно, за исключением мелочей, которых не хватает для полного восприятия всей картины.

    Поясните, пожалуйста, один момент:
    Почему при вызове Функции S1 строка размещается в сегменте данных? По причине явной инициализации?
     
  5. Mika0x65

    Mika0x65 New Member

    Публикаций:
    0
    Регистрация:
    30 июл 2005
    Сообщения:
    1.384
    vb_man
    Из-за синтаксиса фактически. Т.е. 'char *ptr = "abc";' говорит компилятору: "размести строку в секции данных, а во время выполнения ф-ии положи в ptr ее адрес", а 'char ptr[] = "abc";' -- "размести во время выполнения строку в стеке, а в ptr положи ее адрес". Если взять отладчик, например, Olly, то все это можно увидеть в динамике.
     
  6. vb_man

    vb_man New Member

    Публикаций:
    0
    Регистрация:
    19 сен 2009
    Сообщения:
    24
    Понятненько.
    Про ольку, не догадался - посмотрю обязательно.
    Еще раз благодарю.
    Тема закрыта.
     
  7. baldr

    baldr New Member

    Публикаций:
    0
    Регистрация:
    29 апр 2010
    Сообщения:
    327
    Не совсем верно: ptr, в данном случае, не указатель а сам массив/строка (разница в том, что для char *ptr значения выражений ptr и &ptr различны, а для char ptr[] — нет).
     
  8. vb_man

    vb_man New Member

    Публикаций:
    0
    Регистрация:
    19 сен 2009
    Сообщения:
    24
    Спасибо за комментарий!. Ни первый год давлю кнопку F7, но указатели по хорошему никак не хотят в моей голове укладываться.
     
  9. vb_man

    vb_man New Member

    Публикаций:
    0
    Регистрация:
    19 сен 2009
    Сообщения:
    24
    Вчера ночью не догнал о чем Вы! А на самом деле строка действительно издевательски улыбалась моей безграмотности.