Обратный порядок в массиве символов в C

#arrays #c #pointers #reverse

#массивы #c #указатели #обратный

Вопрос:

Указатели меня сильно смущают. У меня есть функция, которая принимает в качестве аргументов argc (количество аргументов, которые являются строками 1, то есть имя кода) и char* argv[] , что, если я правильно понял, представляет собой массив указателей. Теперь в качестве результата мне нужно напечатать в каждой строке аргумент (строку) и перевернутую строку. Это означает, что если я передаю в качестве аргументов hello world, мне нужно иметь:

 hello olleh
world dlrow
  

Я попытался реализовать часть кода:

 int main(int argc, char *argv[])
{
    int i = 1;
    int j;

    while (i < argc)
    {
        while (argv[i][j] != 0) {
            printf("%c", argv[i][j]);
            j  ;
        }
        
        i  ;
    }
    return 0;
}
}
  

И теперь я буквально потерян. Внутренний цикл не работает. Я знаю, что argv[i] проходит через все мои строки аргументов, но мне, очевидно, нужно ввести строки (массив символов), чтобы поменять местами указатели. Также я не понимаю, в чем разница между argv[0] и *argv, потому что теоретически argv[0] выводит первый элемент массива, который является указателем, то есть адресом, но вместо этого он выводит первый аргумент.

Комментарии:

1. Спросите себя, какое значение должно j быть в начале внутреннего while цикла.

Ответ №1:

char* argv[] это «массив указателей на символ» Важно научиться читать типы на C; потому что эти типы позволят / помешают вашей способности что-то делать.

Типы считываются справа налево. [] является типом массива с неопределенным количеством * элементов, является типом указателя, char является базовым типом. Объедините их, и теперь у вас есть «массив указателей на символ»

Итак, чтобы получить что-то из argv , вы должны сначала указать, какой элемент находится в массиве. argv[0] будет указывать первый элемент. Давайте посмотрим, что возвращается. Поскольку массив не является частью результата, ответом будет «указатель на символ»

  char* line = argv[0];
  

захватил бы указатель на символ, который хранится в argv[0] .

В C a char* или «указатель на символ» — это соглашение, используемое для строки. В C нет нового типа для «строки»; скорее он использует указатели на символы, где продвижение указателя в конечном итоге приводит к символу, который сигнализирует о конце строки.

 int main(int argc, char* argv[]) {
   int index = 0;
   while (index <= argc) {
      char* line = argv[index];
      printf("%d, %sn", index, line);
      index  ;
   }
 }
  

следует сбросить аргументы, переданные вашей программе. Оттуда, я полагаю, вы можете справиться с остальным.

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

Удачи!

—- Обновлено для решения вопроса «Как мне их отменить?» —-

Теперь, когда у вас есть простой char* (указатель на символ), как изменить строку на противоположную?

Помните, что строка — это указатель на символ, где следующие символы в конечном итоге заканчиваются символом. Сначала нам нужно будет найти конец строки.

 char* some_string = ...
char* position = some_string;
while (*position != 0) {
  position  ;
}
// end_of_string set, now to walk backwards
while (position != some_string) {
  position--; 
  printf("%c", *end_of_string);
}
  

Комментарии:

1. Итак, как я могу ввести внутри аргумента итерацию по символам?

2. @ElenaFranchini пройдитесь по символам один раз. Не делая этого, вы никогда не узнаете, где заканчиваются символы. Затем начните с конца и возвращайтесь к началу символов, либо сохраняя их в обратном порядке; или, если хранение не требуется, распечатайте их на экране. Я обновлю сообщение, чтобы дать несколько советов.

3. Спасибо, извините за поздний ответ, немного понятно, но есть кое-что, что сбивает с толку. Допустим, у меня есть строка p1=»привет», а с другой стороны, у меня есть массив строк argv, содержащий «привет» «мир». Теперь, если я напечатаю p1, у меня будет строка «hello», поэтому я подумал, что при печати argv у меня должны быть адреса hello и world, но вместо этого у меня есть только адрес hello, почему? Я имею в виду, что печать указателя должна возвращать то, что он содержит, так почему P1 содержит весь массив, а argv содержит только адрес первого элемента, даже если они указывают на оба массива?

4. @ElenaFranchini Следующий адрес в массиве строк будет содержать «мир». Отделите часть массива в своем уме от строковой части. Массив по-прежнему является просто массивом; но это массив указателей.