» УРОК 36 ИСПОЛЬЗОВАНИЕ АРГУМЕНТОВ КОМАНДНОЙ СТРОКИ – c/c . Обзор решений форума программистов –

Что вам необходимо знать

Чтобы увеличить количество приложений, поддерживаемых вашей программой, C позволяет использовать аргументы командной строки. Из урока 37 вы узнаете, как с помощью макрокоманд и констант можно упростить ваше программирование или создать более удобочитаемый код. Однако, прежде чем перейти к уроку 37, убедитесь, что вы освоили следующие основные концепции:

  1. Когда вы запускаете программу из системной подсказки, информация которую вы вводите, становится командной строкой программы.
  2. Чтобы позволить вашим программам обращаться к командной строке C передает функции main два параметра: argc и argv.
  3. Параметр argc содержит количество аргументов командной строки.
  4. Параметр argv представляет собой массив указателей на символьные строки, каждая из которых содержит аргумент командной строки.
  5. В зависимости от вашего компилятора программа может обращаться к третьему параметру main с именем env,который представляет собой массив указателей на символьные строки, содержащие переменные среды.

Предыдущий урок Следующий урок

Передача аргументов в программу. урок 19 курса “основы c”

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

./a.out test.txt
ls -lt /home/peter/

Здесь вызываются программы a.out (из текущего каталога) и ls (из одного каталога, указанного в переменной окружения PATH). Первая программа из командной строки получает одно слово — test.txt, вторая — два: -lt и /home/peter/.

Если программа написана на языке C, то при ее запуске управление сразу передается в функцию main(), следовательно, именно она получает аргументы командной строки, которые присваиваются ее переменным-параметрам.

До этого мы определяли функцию main() так, как-будто она не принимает никакие параметры и ничего не возвращает. На самом деле в языке C любая функция по-умолчанию (если не определено ничего иного) возвращает целое число. В этом можно убедиться. Если записать код таким образом:

main(){printf("Hin");return;}

, то ошибки при компиляции не возникнет (но будет предупреждение). То же самое будет, если записать int main(). Это доказывает, что функция по-умолчанию возвращает целое число, а не ничто (void). Хотя то, что возвращает функция всегда можно “переопределить”, например, voidmain() или float main().

При вызове программы из командной строки в нее всегда передается пара данных:

  1. целое число, обозначающее количество слов (элементов, разделенных пробелами) в командной строке при вызове,
  2. указатель на массив строк, где каждая строка — это отдельное слово из командной строки.

Само имя программы также считается. Например, если вызов выглядит так:

./a.out 12 theme 2

, то первый аргумент программы имеет значение 4, а массив строк определяется как {“./a.out”, “12”, “theme”, “2”}.

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

Эти данные (число и указатель) передаются в программу даже тогда, когда она просто вызывается по имени без передачи в нее чего-либо: ./a.out. В таком случае первый аргумент имеет значение 1, а второй указывает на массив, состоящий всего из одной строки {“./a.out”}.

:/>  Неизвестное устройство в диспетчере устройств: как определить

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

Чтобы получить доступ к переданным в программу данным, их необходимо присвоить переменным. Поскольку аргументы сразу передаются в main(), то ее заголовок должен выглядеть таким образом:

int main(int n, char *arr[])

В первой переменной (n) содержится количество слов, а во второй — указатель на массив строк. Часто второй параметр записывают в виде **arr. Однако это то же самое. Вспомним, что сам массив строк, содержит в качестве своих элементов указатели на строки. А в функцию мы передаем указатель на первый элемент массива. Получается, что передаем указатель на указатель, т.е. **arr.

В программе мы использовали переменные-параметры argc и argv. Принято использовать именно такие имена, но на самом деле они могут быть любыми. Лучше придерживаться этого стандарта, чтобы ваши программы были более понятны не только вам, но и другим программистам.

Если у вас есть опыт работы в командной строке GNU/Linux, вы знаете, что у большинства команд есть ключи и аргументы. Например, при просмотре содержимого каталогов, копировании, перемещении в качестве аргументов указываются объекты файловой системы, над которыми выполняется команда. Особенности ее выполнения определяются с помощью ключей. Например, в команде

cp -r ../les_1 ../les_101 

cp — это имя команды, -r — ключ, а ../les_1 и ../les_101 — аргументы команды.

Нередко в программы при их запуске передаются адреса файлов и “модификаторы” (это ключи) процесса выполнения программы.

Напишем программу, которая открывает указанные пользователем в командной строке файлы на запись или добавление и записывает (добавляет) туда одну и туже информацию, которую пользователь вводит с клавиатуры в процессе выполнения программы:

#include <stdio.h>#include <string.h>
 
int main (int argc,char**argv){int i, ch;
    FILE *f[5];
 
    if(argc <3|| argc >7){puts("Неверное количество параметров");return1;}
 
    if(strcmp(argv[1],"-w")!=&&strcmp(argv[1],"-a")!=){
 
      puts("Первый параметр -w или -a");return2;}
 
    for(i=; i < argc-2; i  ){
      f[i]=fopen(argv[i 2], argv[1] 1);if(f[i]== NULL){printf("Файл %s нельзя открытьn", 
                argv[i 2]);return3;}}
 
    while((ch =getchar())!= EOF)for(i=; i < argc-2; i  )putc(ch,f[i]);
 
    for(i=; i < argc-2; i  )fclose(f[i]);
 
    return;}

Пояснения к коду:

  1. Создается массив из пяти файловых указателей. Следовательно можно одновременно открыть не более пяти файлов. Файловый указатель первого файла будет хранится в элементе массива f[0], второго — в f[1] и т.д.
  2. Проверяется количество аргументов командной строки. Их должно быть не меньше трех, т.к. первый – это имя программы, второй — режим открытия файла, третий — первый или единственный файл, в который будет производится запись. Поскольку программа позволяет открыть только пять файлов, то общее число аргументов командной строки не может быть больше семи. Поэтому если количество аргументов меньше 3 или больше 7, то программа завершается, т.к. оператор return приводит к выходу из функции, даже если после него есть еще код. Возвращаемое из функции значение неравное 0, может быть интерпретировано родительским процессом, как сообщение о том, что программа завершилась с ошибкой.
  3. Проверяется корректность второго аргумента командной строки. Если он не равен ни “-w”, ни “-a”, то условное выражение во втором if возвращает 1 (true). Функция strcmp() позволяет сравнивать строки и возвращает 0 в случае их равенства.
  4. В цикле for открываются файлы по указанным адресам, которые начинаются с третьего элемента массива argv. Именно поэтому к i прибавляется 2, чтобы получать элементы массива argv, начиная с третьего. Выражение argc-2 указывает на количество переданных имен файлов; т.к. в argc хранится общее число аргументов командной строки, первые два из которых не являются именами файлов.
  5. Выражение argv[1] 1 позволяет “вырезать” из строки “-w” (или “-a”) подстроку “w” (или “a”), т.к. argv[1] по сути указатель на первый элемент строки. Прибавляя к указателю единицу, мы смещаем его к следующему элементу массива.
  6. Если файл отрыть не удается, то функция fopen() возвращает NULL. В таком случае программа завершается.
  7. Каждый символ, введенный пользователем с клавиатуры, записывается во все открытые файлы.
  8. В конце файлы закрываются.
:/>  c - How to output special characters in cmd window? - Stack Overflow

Курс с решением части задач:
android-приложение, pdf-версия

Выполнение цикла, пока argv не содержит null

Как вы уже знаете, программы C используют символ NULL для завершения символьной строки. Подобным способом C использует символ NULL, чтобы отметить последний элемент массива argv.Следующая программа ARGVNULL.CPP изменяет оператор for предыдущей программы, чтобы выполнять цикл по элементам argv, пока текущий элемент argv не будет равен NULL:

#include <iostream.h>

void main(int argc, char *argv[])

{
int i;
for (i = 0; argv != NULL; i ) cout << «argv[» << i << «] содержит » << argv << endl;
}

Доступ к переменным среды операционной системы

Как вы знаете, большинство операционных систем позволяют вам определять переменные среды, к которым ваши программы могут обращаться для определения разных параметров, таких как командный путь. Например, если вы используете среду MS-DOS, вы устанавливаете или выводите переменные среды с помощью команды SET.

В зависимости от типа вашего компилятора вы можете обращаться к переменным среды из вашей программы, используя третий параметр main с именем env.Подобно параметру argv, параметр env представляет собой указатель на массив указателей на символьные строки.

void main(int argc, char *argv[], char *env[])

Следующая программа SHOWENV.CPP выполняет цикл по элементам массива env для вывода переменных среды программы:

#include <iostream.b>

void main(int argc, char *argv[], char *env[])

{
while (*env) cout << *env << endl;
}

Как видите, программа просто выполняет цикл по элементам массива env,пока не встретит указатель NULL, который указывает последнюю запись массива. Если вы откомпилируете и запустите эту программу, она выведет ваши переменные среды, как показано ниже:

С:> SHOWENV <ENTER>

ТЕМР=С:WINDOWSTEMP

PROMPT=$p$g

COMSPEC=C:WINDOWSCOMMAND.СОМ

РАТН=С:WINDOWS;С:DOS

Доступ к переменным среды

В зависимости от типа компилятора, ваши программы могут обращаться к переменным среды операционной системы, используя третий параметр функции main с именем env. Подобно параметру argv, параметр env представляет собой массив указателей на символьные строки, каждый из которых указывает переменную среды. Чтобы обратиться к переменным среды, используя параметр env, измените заголовок функции main следующим образом:

:/>  Запуск от имени администратора программ и командной строки

void main(int argc, char *argv[], char *env[])

Отладка программы с аргументами командной строки

Для передачи аргументов командной строки при отладке программы необходимо обратиться к меню Свойства проекта.
Вкладка Свойства проекта
На вкладке Свойства конфигурации ->Отладка выбрать Аргументы команды и задать их значения.
Аргументы командной строки при отладке

При запуске программы в режиме отладки введенные аргументы будут восприниматься программой как аргументы командной строки.Назад

Назад:

Язык C

Пример использования

Давайте рассмотрим программу, которая объединяет две строки, заданные в качестве входных данных.

Мы передадим в нашу программу два аргумента командной строки, поэтому общее argc должно быть 3 (включая имя программы).

Мы можем написать нашу программу так:

#include <iostream> 
#include <string>
 
using namespace std;
 
string concat_strings(string s1, string s2) {
    return s1   s2;
}
 
int main(int argc, char* argv[]) 
{ 
    cout << "You have entered " << argc 
         << " arguments:" << "n";
 
    if (argc != 3) {
        cerr << "Program is of the form: " << argv[0] << " <inp1> <inp2>n";
        return 1;
    } 
 
    string result = concat_strings(argv[1], argv[2]);
 
    cout << "Result: " << result << endl;
 
    return 0; 
} 

Если исполняемое имя test.out, на компьютере с Linux запускаем исполняемый файл с помощью этой команды:

./test.out Hello _ArduinoPlus

Обратите внимание, что аргументы разделены пробелом. Таким образом у нас аргументы командной строки: «Hello» и «_ArduinoPlus».

На выходе получаем:

You have entered 3 arguments:                                                                                                
Result: Hello_ArduinoPlus

Отлично! Похоже, что всё работает как и ожидалось, так как первый аргумент – название самой программы.

Попробуем теперь запустить программу с 4 аргументами.

./test.out Hello from ArduinoPlus

На выходе получаем:

You have entered 4 arguments:                                                                                                
Program is of the form: ./test.out <inp1> <inp2>

Действительно, программа выдает нам правильное сообщение об ошибке!

Трактовка argv как указателя

Как вы уже знаете, C позволяет вам обращаться к элементам массивов, используя указатели. Следующая программа ARGVPTR.CPP трактует argvкак указатель на указатель символьной строки (другими словами, указатель на указатель), чтобы вывести содержимое командной строки:

#include <iostream.h>

void main(int argc, char **argv)

{
int i = 0;
while (*argv) cout << «argv[» << i << «] содержит » << *argv << endl;
}

Выберите время, чтобы проанализировать объявление параметра argvв main:

void main(int argc, char **argv)


Первая звездочка в объявлении сообщает компилятору C , что argvпредставляет собой указатель. Вторая звездочка сообщает компилятору, что argv представляет собой указатель на указатель — в данном случае указатель на указатель типа char. Представьте argv как массив указателей. Каждый элемент массива в данном случае указывает на массив типа char.

Оставьте комментарий

Adblock
detector