Введите первую строку в bash, а затем отобразите эту переменную, вот что вы увидите:
$ tmpdir=/cygdrive/c/workdir\ \(newco\,\ LLC\)
$ echo $tmpdir
/cygdrive/c/workdir (newco, LLC)
Если еще не ясно, кто виноват, добавьте echo
в начале второй строки и заключите его в двойные кавычки. Вы увидите, какая команда на самом деле выполняется:
$ echo "tail -n +2 $tmpdir/workfile.txt > $tmpdir/workfile2.txt"
tail -n +2 /cygdrive/c/workdir (newco, LLC)/workfile.txt > /cygdrive/c/workdir (newco, LLC)/workfile2.txt
Вы правильно избежали назначения переменных, но этого недостаточно. Bash выполняет простую подстановку подстрок, тем самым вставляя дополнительные пробелы и нарушая вашу команду.
Как @savanto предложил в своем ответе, вы можете заключить переменные в двойные кавычки, чтобы лишние пробелы не обрабатывались как разделители аргументов. Эта строка:
tail -n +2 "${tmpdir}/workfile.txt" > "${tmpdir}/workfile2.txt"
будет выглядеть так после подстановки переменной:
tail -n +2 "/cygdrive/c/workdir (newco, LLC)/workfile.txt" > "/cygdrive/c/workdir (newco, LLC)/workfile2.txt"
Это наиболее распространенный и предпочтительный способ решения этой проблемы. Если вы отчаянно хотите избежать двойных кавычек, вы можете попробовать двойное экранирование: сначала при присваивании, затем после подстановки.
$ tmpdir=/cygdrive/c/workdir\\\ \\\(newco\\\,\\\ LLC\\\)
$ echo $tmpdir
/cygdrive/c/workdir\ \(newco\,\ LLC\)
Быстрое объяснение тройной обратной косой черты: обратная косая черта означает: «обрабатывать следующий символ как обычный символ, игнорировать любое специальное значение» (т.е. избегать его). Первая обратная косая черта является escape-символом, поэтому вторая будет рассматриваться как обратная косая черта, а не как escape-символ. Таким образом, двойной обратный слеш производит один обратный слеш. Третий просто избегает следующего символа, такого как пробел или скобка. Например, a\\\ b
станет a\ b
.
Теперь, если мы подставим переменные в вашу команду, она будет экранирована правильно:
tail -n +2 /cygdrive/c/workdir\ \(newco\,\ LLC\)/workfile.txt > /cygdrive/c/workdir\ \(newco\,\ LLC\)/workfile2.txt