Сцепление строки с собой два раза дает ошибку сегментации - PullRequest
3 голосов
/ 22 ноября 2011
#include <stdio.h>

int main(void)
{
    char a[100] = "hi";

    strcat(a, a);
    strcat(a, a);

    printf("%s\n", a);

    return 0;
}

Ответы [ 4 ]

9 голосов
/ 22 ноября 2011

Из определения strcat в стандарте языка C, §7.21.3.1/2

If copying takes place between objects that overlap, the behavior is undefined.

Мой компилятор падает, даже если он выполняется один раз, так как strcat(a, a); копирует первыйсимвол второго аргумента над '\ 0' в конце первого аргумента, затем второй символ второго аргумента после него и т. д., пока он не встретит '\ 0' во втором аргументе ... что никогда не происходит, потому что«\ 0» исчезло, когда был скопирован первый символ.

5 голосов
/ 22 ноября 2011

С man-страницы strcat (3):

DESCRIPTION

The strcat() and strncat() functions append a copy of the null-terminated
string s2 to the end of the null-terminated string s1, then add a termi-
nating '\0'. The string s1 must have sufficient space to hold the
result.

The strncat() function appends not more than n characters from s2, and
then adds a terminating \ 0 '.

The source and destination strings should not overlap, as the behavior is
undefined.

2 голосов
/ 22 ноября 2011

Это неопределенное поведение.

Если вы в цикле, читаете каждый char из строки, пока не будет найдено \0, но в то же время вы добавляете (пишете)символы до конца, когда закончится цикл?

0 голосов
/ 22 ноября 2011

Я подозреваю, что это потому, что реализация перезаписывает нулевой байт в конце:

Start: a = {h,i,\0}
         src^   vdst
next:  a = {h,i,h}
           src^   vdst
next:  a = {h,i,h,i}
             src^   vdst
next:  a = {h,i,h,i,h}
...

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

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...