2017-02-09 19 views
0

Это оказывается удивительно трудно сделать, и мне еще предстоит найти прямое решение, просматривающее существующие вопросы. Я просмотрел несколько повторяющихся вопросов, но они не то, что я ищу.C - Получить подстроку после первых n символов строки

Я пробовал что-то вроде этого, но я явно не понимаю, как работает strncpy. Я хочу получить все текста после первые 14 символов строки.

int length = sizeof(str) - 14; 
strncpy(substr, str+14, length); 

Каков самый простой способ сделать это?

+1

ли вы, возможно, означает, 'длина ИНТ = STRLEN (НТР) - 14;'? Я предполагаю, что вы проверяете, что это как минимум 15 символов. – AntonH

+0

Что такое объявление 'str'? –

+0

Кроме того, что не так, просто используя 'strcpy'? 'strcpy (substr, str + 14);' – AntonH

ответ

1

Я пробовал что-то вроде этого, но я явно не понимаю, как работает strncpy. Я хочу получить весь текст после первых 14 символов строки.

int length = strlen(str) - 14; 
if(length >= 0) { 
    strncpy(substr, str+13, length); 
    substr[length] = '\0'; 
} 
+0

@IharobAlAsimi, спасибо за предложение. Я отредактировал ответ. – VHS

+0

В приведенном выше коде не указан заявленный цель: * Я хочу получить весь текст ** после ** первых 14 символов строки. * Он использует 'strncpy()' без причины. Это эквивалентно 'strcpy (substr, str + 13);', более простой и читаемый, но все же с неправильным смещением. – chqrlie

+0

@chqrlie, вы можете прочитать между строк в вопросе OP. Цель состоит не только в достижении цели, но и в развитии понимания «strncpy», который мой ответ пытается обеспечить. – VHS

4

Вы неправильно понимаете, как работает математика? 10 - 14 = -4

EDIT:

Был

char str[10]; 
int length = sizeof(str) - 14; 

ИНТ исходное сообщение. (см правок)

Кроме того, вы не должны использовать sizeof, чтобы вычислить длину строки, используйте strlen(). Оператор sizeof используется для определения размера типа, если str является массивом или указателем sizeof будет возвращать количество элементов в первом случае и размер указателя, эквивалентный sizeof(void *) во втором.

Строка представляет собой массив, но размер такого массива не является длиной строки, строка из 10 символов может быть сохранена в массиве из 100 элементов, поэтому проблема не в strncpy (), которую вы должны избегайте BTW, потому что он не гарантирует nul завершение), настоящая проблема заключается в том, как вы его обрабатываете.

Предположим, у вас есть действительная строка длины ≥ 14, а затем

strcpy(substr, str + 14) 

должно быть достаточно!

Вы должны убедиться, что целевой массив substr достаточно, конечно, большой, и что длина str больше или равна или, вы в любом из обоих случаях вызвать неопределенное поведение.

Если вы ранее знаете длину str то, вы можете попробовать

memcpy(substr, str + 14, length_str - 14); 
substr[length_str - 14] = '\0'; 

substr отмечают, что должен иметь по крайней мере length_str - 14 элементов +1 для nul терминатора, а также, если вы знаете, что есть '\0' терминатор в str, затем

// Leaving + 1 explicitly to denote the '\0' 
memcpy(substr, str + 14, length_str - 14 + 1); 

должны скопировать его в одном вызове.

1

Есть 2 проблемы в вашей попытке:

  • sizeof(str) не Подсчитать количество символов в строке, на которую указывает str. Он оценивает размер str, который может быть указателем или массивом, поскольку вы не опубликовали определение. Для этой цели вы должны использовать strlen(str).

  • strncpy()не делает, что вы думаете,. Эта функция очень подвержена ошибкам. Это никогда не является подходящим инструментом для любой работы, не используйте ее.

Решение простое: если вы знаете, что str имеет по крайней мере 14 символов и substr указывает на массив достаточно долго, чтобы получить остальную часть строки, просто написать следующее:

strcpy(substr, str + 14); // copy all characters, skipping the first 14 bytes 

Если str может иметь меньше, чем 14 символов, тест:

*substr = '\0'; 
if (strlen(str) >= 14) { 
    strcpy(substr, str + 14); 
} 

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

*substr = '\0'; 
if (strlen(str) >= 14) { 
    snprintf(substr, substr_size, "%s", str + 14); 
} 

Или эта альтернатива:

*substr = '\0'; 
if (strlen(str) >= 14) { 
    // copy at most substr_size-1 characters from str, skipping the first 14 bytes. 
    // and null terminate the destination string. 
    strncat(substr, substr_size - 1, str + 14); 
}