Как передать параметры в & ldquo; nohup & rdquo; Баш? [Дубликат]

Это зависит от текущей культуры текущей культуры потоков.

float.Parse("123,5", system.threading.thread.currentthread.currentculture); 

float.Parse("123.5", system.threading.thread.currentthread.currentculture); 

ЕСЛИ вы строго не хотите, чтобы специфические культуры были тогда

float.Parse("123.5", CultureInfo.InvariantCulture);
877
задан codeforester 1 March 2017 в 20:32
поделиться

12 ответов

Псевдоним Bash напрямую не принимает параметры. Вам нужно будет создать функцию и псевдоним.

alias не принимает параметры, но функцию можно вызвать так же, как псевдоним. Например:

myfunction() {
    #do things with parameters like $1 such as
    mv "$1" "$1.bak"
    cp "$2" "$1"
}


myfunction old.conf new.conf #calls `myfunction`

Кстати, функции Bash, определенные в вашем .bashrc, и другие файлы доступны как команды внутри вашей оболочки. Так, например, вы можете вызвать более раннюю функцию, подобную этой

$ myfunction original.conf my.conf
1515
ответ дан arunkumar 17 August 2018 в 08:55
поделиться
  • 1
    Должен ли я обернуть $1 в кавычки? – Jürgen Paul 15 July 2013 в 07:43
  • 2
    Вам даже не нужно объявлять псевдоним. Просто определение функции будет выполнено. – dinigo 10 December 2013 в 14:57
  • 3
    Если вы изменяете псевдоним функции, source вашего .bashrc добавит эту функцию, но она не удалит старый псевдоним. Поскольку псевдонимы имеют более высокий прецедент, чем функции, он попытается использовать псевдоним. Вам нужно либо закрыть, либо снова открыть свою оболочку, либо вызвать unalias <name>. Возможно, я спасу кого-то за 5 минут, которые я просто потратил впустую. – Marty Neal 21 May 2014 в 18:25
  • 4
    @MartinNeal: Один из трюков, с которыми я научился в Sun, - это просто exec bash: он запустит новую оболочку, предоставив вам чистую информацию о ваших конфигурациях, точно так же, как если бы вы закрылись и снова открылись, но сохранили среду этого сеанса переменные настройки тоже. Кроме того, выполнение bash без exec может быть полезно, когда вы хотите обрабатывать мысли как стек. – Macneil Shonle 9 July 2014 в 17:39
  • 5
    @mich - да, всегда ставьте переменные bash в кавычки. например mv "$1" "$1.bak". без кавычек, если $ 1 был «hello world», вы выполнили бы mv hello world hello world.bak вместо mv "hello world" "hello world.bak". – orion elenzil 11 June 2015 в 16:17

Для принятия параметров вы должны использовать функции!

Однако $ @ get интерпретируется при создании псевдонима, а не во время выполнения псевдонима, а escape-код не работает. Как решить эту проблему?

Вам нужно использовать функцию оболочки вместо псевдонима, чтобы избавиться от этой проблемы. Вы можете определить foo следующим образом:

function foo() { /path/to/command "$@" ;}

ИЛИ

foo() { /path/to/command "$@" ;}

Наконец, вызовите ваш foo (), используя следующий синтаксис:

foo arg1 arg2 argN

Убедитесь, что вы добавили файл foo () в ~/.bash_profile или ~/.zshrc.

В вашем случае это будет работать

function trash() { mv $@ ~/.Trash; }
2
ответ дан Ahmad Awais 17 August 2018 в 08:55
поделиться
  • 1
    Я не понимаю твою идею. Я думаю, что это не важно, когда аргументы интерпретируются. Aliase принимает столько параметров, сколько вы хотите в конце. – Timo 18 October 2017 в 19:41
  • 2
    Но лучше делать это с помощью функций. Псевдонимы не предназначены для этого. – Ahmad Awais 18 October 2017 в 20:21

Альтернативным решением является использование marker - инструмента, который я создал недавно, который позволяет вам «закладок» шаблонов команд и легко помещать курсор в держатели команд:

commandline marker [/g1]

Я обнаружил, что большую часть времени я использую функции оболочки, поэтому мне не нужно писать часто используемые команды снова и снова в командной строке. Проблема использования функций для этого варианта использования заключается в добавлении новых терминов в словарь моей команды и необходимости запоминать, какие параметры функций относятся к реальной команде. Цель маркера - устранить эту психическую нагрузку.

26
ответ дан Amine Hajyoussef 17 August 2018 в 08:55
поделиться
  • 1
    Большое спасибо за создание этого! Я давно искал такое решение! – Harsh Trivedi 6 June 2018 в 02:01

Вот три примера функций, которые у меня есть в моем ~/.bashrc, которые являются по существу алиасами, которые принимают параметр:

#Utility required by all below functions.
#https://stackoverflow.com/questions/369758/how-to-trim-whitespace-from-bash-variable#comment21953456_3232433
alias trim="sed -e 's/^[[:space:]]*//g' -e 's/[[:space:]]*\$//g'"

.

:<<COMMENT
    Alias function for recursive deletion, with are-you-sure prompt.

    Example:
        srf /home/myusername/django_files/rest_tutorial/rest_venv/

    Parameter is required, and must be at least one non-whitespace character.

    Short description: Stored in SRF_DESC

    With the following setting, this is *not* added to the history:
        export HISTIGNORE="*rm -r*:srf *"
    - https://superuser.com/questions/232885/can-you-share-wisdom-on-using-histignore-in-bash

    See:
    - y/n prompt: https://stackoverflow.com/a/3232082/2736496
    - Alias w/param: https://stackoverflow.com/a/7131683/2736496
COMMENT
#SRF_DESC: For "aliaf" command (with an 'f'). Must end with a newline.
SRF_DESC="srf [path]: Recursive deletion, with y/n prompt\n"
srf()  {
    #Exit if no parameter is provided (if it's the empty string)
        param=$(echo "$1" | trim)
        echo "$param"
        if [ -z "$param" ]  #http://tldp.org/LDP/abs/html/comparison-ops.html
        then
          echo "Required parameter missing. Cancelled"; return
        fi

    #Actual line-breaks required in order to expand the variable.
    #- https://stackoverflow.com/a/4296147/2736496
    read -r -p "About to
    sudo rm -rf \"$param\"
Are you sure? [y/N] " response
    response=${response,,}    # tolower
    if [[ $response =~ ^(yes|y)$ ]]
    then
        sudo rm -rf "$param"
    else
        echo "Cancelled."
    fi
}

.

:<<COMMENT
    Delete item from history based on its line number. No prompt.

    Short description: Stored in HX_DESC

    Examples
        hx 112
        hx 3

    See:
    - https://unix.stackexchange.com/questions/57924/how-to-delete-commands-in-history-matching-a-given-string
COMMENT
#HX_DESC: For "aliaf" command (with an 'f'). Must end with a newline.
HX_DESC="hx [linenum]: Delete history item at line number\n"
hx()  {
    history -d "$1"
}

.

:<<COMMENT
    Deletes all lines from the history that match a search string, with a
    prompt. The history file is then reloaded into memory.

    Short description: Stored in HXF_DESC

    Examples
        hxf "rm -rf"
        hxf ^source

    Parameter is required, and must be at least one non-whitespace character.

    With the following setting, this is *not* added to the history:
        export HISTIGNORE="*hxf *"
    - https://superuser.com/questions/232885/can-you-share-wisdom-on-using-histignore-in-bash

    See:
    - https://unix.stackexchange.com/questions/57924/how-to-delete-commands-in-history-matching-a-given-string
COMMENT
#HXF_DESC: For "aliaf" command (with an 'f'). Must end with a newline.
HXF_DESC="hxf [searchterm]: Delete all history items matching search term, with y/n prompt\n"
hxf()  {
    #Exit if no parameter is provided (if it's the empty string)
        param=$(echo "$1" | trim)
        echo "$param"
        if [ -z "$param" ]  #http://tldp.org/LDP/abs/html/comparison-ops.html
        then
          echo "Required parameter missing. Cancelled"; return
        fi

    read -r -p "About to delete all items from history that match \"$param\". Are you sure? [y/N] " response
    response=${response,,}    # tolower
    if [[ $response =~ ^(yes|y)$ ]]
    then
        #Delete all matched items from the file, and duplicate it to a temp
        #location.
        grep -v "$param" "$HISTFILE" > /tmp/history

        #Clear all items in the current sessions history (in memory). This
        #empties out $HISTFILE.
        history -c

        #Overwrite the actual history file with the temp one.
        mv /tmp/history "$HISTFILE"

        #Now reload it.
        history -r "$HISTFILE"     #Alternative: exec bash
    else
        echo "Cancelled."
    fi
}

Ссылки:

7
ответ дан Community 17 August 2018 в 08:55
поделиться
  • 1
    Нет, он работает точно так же, как функция. Как объясняют некоторые из ответов, вы не можете создать псевдоним, который принимает параметр. Что вы можете сделать, это написать функцию, которую вы сделали. – tripleee 13 January 2015 в 06:01
  • 2
    @tripleee С моей точки зрения новичков bash, прежде чем читать свой комментарий, я подумал, что это псевдоним (альтернативный способ его создания). Он функционирует точно как один, насколько я могу судить. Это по существу псевдоним, который принимает параметр, даже если я отключен по терминологии. Я не вижу проблемы. Я уточнил ссылку на другой ответ в этой проблеме. Это помогло мне создать это. – aliteralmind 13 January 2015 в 06:04
  • 3
    Возможно, это не отвечает конкретно на вопрос «псевдоним bash, который принимает параметр», потому что теперь я понимаю, что это невозможно, но это, безусловно, эффективно отвечает на него. Что мне здесь не хватает? – aliteralmind 13 January 2015 в 06:23
  • 4
    Некоторые действительно хорошие примеры здесь, и красиво прокомментированный код. Отличная помощь людям, пришедшим на эту страницу. – chim 25 March 2015 в 13:09
  • 5
    Этот ответ очень длинный и полный информации. Там столько информации, что я не могу сказать, отвечает ли он на вопрос или нет. – byxor 4 October 2016 в 16:41

Есть законные технические причины, чтобы хотеть обобщенного решения проблемы псевдонимов bash, не имеющего механизма для принятия произвольных аргументов. Одна из причин заключается в том, что на команду, которую вы хотите выполнить, будет оказано неблагоприятное воздействие на изменения среды, возникающие в результате выполнения функции. Во всех других случаях следует использовать функции.

Что недавно заставило меня попытаться решить это, так это то, что я хотел создать некоторые сокращенные команды для печати определений переменных и функции. Поэтому я написал некоторые функции для этой цели. Однако есть определенные переменные, которые (или могут быть) изменены самим вызовом функции. Среди них:

FUNCNAME BASH_SOURCE BASH_LINENO BASH_ARGC BASH_ARGV

Основная команда, которую я использовал (в функции) для печати переменных defns. в форме, выводимой командой set:

sv () { set | grep --color=never -- "^$1=.*"; }

Например:

> V=voodoo
sv V
V=voodoo

Проблема: это не будет печатать определения упомянутых выше переменных, поскольку они находятся в текущий контекст , например, если в приглашении интерактивной оболочки (или нет в каких-либо вызовах функций) FUNCNAME не определен. Но моя функция говорит мне неправильную информацию:

> sv FUNCNAME
FUNCNAME=([0]="sv")

Одно из решений, о которых я говорил, упоминалось другими в других сообщениях по этой теме. Для этой конкретной команды для печати переменной defns. И которая требует только одного аргумента, я сделал это:

alias asv='(grep -- "^$(cat -)=.*" <(set)) <<<'

Что дает правильный вывод (none) и статус результата (false):

> asv FUNCNAME
> echo $?
1

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

Общее решение для передачи произвольных аргументов команде с псевдонимом Bash:

# (I put this code in a file "alias-arg.sh"):

# cmd [arg1 ...] – an experimental command that optionally takes args,
# which are printed as "cmd(arg1 ...)"
#
# Also sets global variable "CMD_DONE" to "true".
#
cmd () { echo "cmd($@)"; declare -g CMD_DONE=true; }

# Now set up an alias "ac2" that passes to cmd two arguments placed
# after the alias, but passes them to cmd with their order reversed:
#
# ac2 cmd_arg2 cmd_arg1 – calls "cmd" as: "cmd cmd_arg1 cmd_arg2"
#
alias ac2='
    # Set up cmd to be execed after f() finishes:
    #
    trap '\''cmd "${CMD_ARGV[1]}" "${CMD_ARGV[0]}"'\'' SIGUSR1;
    #        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    #       (^This is the actually execed command^)
    #
    # f [arg0 arg1 ...] – acquires args and sets up trap to run cmd:
    f () {
        declare -ag CMD_ARGV=("$@");  # array to give args to cmd
        kill -SIGUSR1 $$;             # this causes cmd to be run
        trap SIGUSR1;                 # unset the trap for SIGUSR1
        unset CMD_ARGV;               # clean up env...
        unset f;                      # incl. this function!
    };
    f'  # Finally, exec f, which will receive the args following "ac2".

Например:

> . alias-arg.sh
> ac2 one two
cmd(two one)
>
> # Check to see that command run via trap affects this environment:
> asv CMD_DONE
CMD_DONE=true

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

Например,

Если вы хотите «$ @», используйте «$ {CMD_ARGV [@]}».

Если вы хотите «$ #», используйте «$ {# CMD_ARGV [@]}».

Etc.

2
ответ дан crobc1 17 August 2018 в 08:55
поделиться

Вопрос просто задан неправильно. Вы не делаете псевдоним, который принимает параметры, потому что alias просто добавляет второе имя для того, что уже существует. Функцией, требуемой OP, является команда function для создания новой функции. Вам не нужно псевдонизировать функцию, поскольку функция уже имеет имя.

Я думаю, вы хотите что-то вроде этого:

function trash() { mv "$@" ~/.Trash; }

Вот и все! Вы можете использовать параметры $ 1, $ 2, $ 3 и т. Д. Или просто использовать их все с помощью $ @

78
ответ дан Evan Langlois 17 August 2018 в 08:55
поделиться
  • 1
    В этом ответе говорится все. Если бы я прочитал снизу этой страницы, я бы сэкономил некоторое время. – joe 28 February 2016 в 20:53
  • 2
    -1 Псевдоним и функция не эквивалентны ... echo -e '#!/bin/bash\nshopt -s expand_aliases\nalias asrc='\''echo "${BASH_SOURCE[0]}"'\'' # note the '\''s\nfunction fsrc(){ echo "${BASH_SOURCE[0]}";}'>>file2&&echo -e '#!/bin/bash\n. file2\nalias rl='\''readlink -f'\''\nrl $(asrc)\nrl $(fsrc)'>>file1&&chmod +x file1&&./file1;rm -f file1 file2 – Fuzzy Logic 9 May 2016 в 07:44
  • 3
    Вы действительно должны цитировать $@ для поддержки файлов с пробелами и т. Д. – Tom Hale 28 March 2017 в 06:26
  • 4
    Предполагалось, что это общее объяснение, что у вас нет параметров псевдонимов, вместо этого вы используете функцию. Данная функция была просто примером для противодействия исходному примеру. Я не думаю, что человек искал функцию общего назначения. Однако, в интересах представления лучшего кода, я обновил ответ. – Evan Langlois 10 August 2017 в 05:16
  • 5
    @FuzzyLogic - я потратил несколько минут, пытаясь распаковать код в ваш комментарий. Это много (интересного) усилия, чтобы пройти, чтобы упаковать код в комментарий, где вы не можете его правильно отформатировать. Я до сих пор не понял, что он делает или, что более важно, почему он поддерживает ваше (правильное) утверждение. – Joe 25 September 2017 в 23:17

Однако вам не нужны функции при создании псевдонимов в файле .bashrc. Например,

# create an alias that takes port-number by the user
alias serve="python -m SimpleHTTPServer $1"

После внесения изменений в файл .bashrc убедитесь, что вы вводите следующую команду:

~$ source .bashrc

Вы должны использовать это, как

~$ serve 8998
-3
ответ дан kaizer1v 17 August 2018 в 08:55
поделиться
  • 1
    Это не верно. $1 расширяется, когда вы определяете псевдоним, потому что он находится внутри двойных кавычек. Поскольку он, вероятно, пуст, ваш псевдоним просто расширяется до python -m SimpleHTTPServer. Единственная причина, по которой это работает, состоит в том, что параметры вашей команды находятся в конце, она не будет работать с параметрами посередине, как в проблеме OP. – Barmar 29 January 2018 в 18:15

Если вы ищете общий способ применения всех параметров к функции, а не только одну или две или некоторые другие жестко закодированные суммы, вы можете сделать это следующим образом:

#!/usr/bin/env bash

# you would want to `source` this file, maybe in your .bash_profile?
function runjar_fn(){
    java -jar myjar.jar "$@";
}

alias runjar=runjar_fn;

Итак, в в приведенном выше примере, я передаю все параметры с того момента, когда я запустил runjar в псевдоним.

Например, если бы я сделал runjar hi there, это закончилось бы фактически запуском java -jar myjar.jar hi there. Если бы я сделал runjar one two three, он запустил бы java -jar myjar.jar one two three.

Мне нравится это решение на $@, потому что оно работает с любым количеством параметров.

1
ответ дан Micah 17 August 2018 в 08:55
поделиться
  • 1
    почему бы не просто назвать функцию runjar вместо того, чтобы сделать ее псевдонимом для функции? Кажется излишне сложным! – Evan Langlois 21 December 2015 в 19:34
  • 2
    Функции @EvanLanglois автоматически alias -ed (или имеющие свойства вещей, переданных в alias) в файлах bash? если да, то это просто мой, не узнав, что – Micah 22 December 2015 в 13:58
  • 3
    Не понимаю, что вы имеете в виду. Псевдоним - это другое имя, будь то человек или функция. Итак, вы создали функцию, затем вы сделали второе имя для функции. Нет ничего особенного в псевдониме, его просто второе имя и не требуется. То, что вы вводите в командной строке, может быть внутренними или внешними функциями, поэтому & quot; function & quot; делает новую команду, а не псевдоним. – Evan Langlois 8 January 2016 в 07:29
  • 4
    Это бессмысленно. Это то же самое, что и alias runjar='java -jar myjar.jar'. Псевдонимы принимают аргументы, но только в конце. – Tom Hale 26 February 2017 в 08:45

Исправляя ответ выше, вы можете получить синтаксис с 1 строкой, как вы можете, для псевдонимов, что более удобно для ad-hoc-определений в файлах оболочки или .bashrc:

bash$ myfunction() { mv "$1" "$1.bak"; cp "$2" "$1"; }

bash$ myfunction original.conf my.conf

Забудьте о полуколонии перед закрывающей правой скобкой. Аналогично, для актуального вопроса:

csh% alias junk="mv \\!* ~/.Trash"

bash$ junk() { mv "$@" ~/.Trash/; }

Или:

bash$ junk() { for item in "$@" ; do echo "Trashing: $item" ; mv "$item" ~/.Trash/; done; }
141
ответ дан Mike Gleason 17 August 2018 в 08:55
поделиться
  • 1
    Я предпочитаю этот ответ, поскольку он показывает итерацию через массив аргументов, которые могут возникнуть. $ 1 и $ 2 - это только особые случаи, которые также проиллюстрированы в этом ответе. – philo vivero 18 September 2014 в 23:04
  • 2
    Измените mv "$1" "$1.bak"; cp "$2" "$1" на mv "$1" "$1.bak" && cp "$2" "$1", чтобы не потерять свои данные, когда mv попадает в неисправность (например, полная файловая система). – Henk Langeveld 23 January 2016 в 13:10
  • 3
    «Не забывайте, что точка с запятой перед закрывающей правой скобкой». Много раз это! Благодаря :) – Kaushal Modi 22 February 2018 в 18:53
  • 4
    И пробелы после первой скобки и до последней скобки также требуются. – Bryan Chapel 17 April 2018 в 21:54

NB: Если идея не очевидна, это плохая идея использовать псевдонимы для чего угодно, кроме псевдонимов, первая из которых является «функцией в псевдониме», а вторая - «трудно читаемой переадресацией / источник'. Кроме того, есть недостатки (которые, по мнению i , были очевидны, но на всякий случай вы сбиты с толку: я не хочу, чтобы они действительно использовались ... где угодно!) [/ ​​G2]

.................................................. .................................................. ............................................

Я уже говорил об этом раньше, и в прошлом это всегда было так:

alias foo='__foo() { unset -f $0; echo "arg1 for foo=$1"; }; __foo()'

, что прекрасно и хорошо, если только вы не избегаете использования функций вместе. в этом случае вы можете воспользоваться огромной способностью bash перенаправлять текст:

alias bar='cat <<< '\''echo arg1 for bar=$1'\'' | source /dev/stdin'

Они оба примерно одинаковой длины дают или принимают несколько символов.

real кикер - это разница во времени, верхняя часть - это «метод функции», а нижняя - метод «перенаправление-источник». Чтобы доказать эту теорию, время говорит само за себя:

arg1 for foo=FOOVALUE
 real 0m0.011s user 0m0.004s sys 0m0.008s  # <--time spent in foo
 real 0m0.000s user 0m0.000s sys 0m0.000s  # <--time spent in bar
arg1 for bar=BARVALUE
ubuntu@localhost /usr/bin# time foo FOOVALUE; time bar BARVALUE
arg1 for foo=FOOVALUE
 real 0m0.010s user 0m0.004s sys 0m0.004s
 real 0m0.000s user 0m0.000s sys 0m0.000s
arg1 for bar=BARVALUE
ubuntu@localhost /usr/bin# time foo FOOVALUE; time bar BARVALUE
arg1 for foo=FOOVALUE
 real 0m0.011s user 0m0.000s sys 0m0.012s
 real 0m0.000s user 0m0.000s sys 0m0.000s
arg1 for bar=BARVALUE
ubuntu@localhost /usr/bin# time foo FOOVALUE; time bar BARVALUE
arg1 for foo=FOOVALUE
 real 0m0.012s user 0m0.004s sys 0m0.004s
 real 0m0.000s user 0m0.000s sys 0m0.000s
arg1 for bar=BARVALUE
ubuntu@localhost /usr/bin# time foo FOOVALUE; time bar BARVALUE
arg1 for foo=FOOVALUE
 real 0m0.010s user 0m0.008s sys 0m0.004s
 real 0m0.000s user 0m0.000s sys 0m0.000s
arg1 for bar=BARVALUE

Это нижняя часть около 200 результатов, выполненных с произвольными интервалами. Кажется, что создание / уничтожение функции занимает больше времени, чем перенаправление. Надеюсь, это поможет будущим посетителям в этом вопросе (не хотел держать это в себе).

4
ответ дан osirisgothra 17 August 2018 в 08:55
поделиться
  • 1
    Имея псевдоним, который определяет функцию, выполните эту функцию просто глупо. Просто напишите функцию. Для почти всех целей псевдонимы заменяются функциями оболочки. – geirha 20 May 2015 в 18:50
  • 2
    в случае, если вы не прочитали все это, что вы могли бы попробовать, я иллюстрировал, почему использование метода функции не было таким же хорошим, в первую очередь, и, более того, это не глупо. Прекратите публикацию и downvoting только потому, что вам лично это не понравилось ... или, по крайней мере, дать правильное объяснение. Вызов названия - это первый знак близкого мышления ... – osirisgothra 20 May 2015 в 19:03
  • 3
    Второй (алиас) имеет несколько побочных эффектов. Во-первых, команда не может использовать stdin. Во-вторых, если после псевдонима не заданы аргументы, любые аргументы, которые, по-видимому, передают оболочке, вместо этого передаются. Использование функции позволяет избежать всех этих побочных эффектов. (Также бесполезное использование кошки). – geirha 20 May 2015 в 19:31
  • 4
    эй, я никогда не говорил, что это хорошая идея, чтобы сделать что-либо из этого, я просто сказал, что есть и другие способы сделать это - основная идея здесь заключается в том, что вы не должны использовать функции в псевдонимах, потому что они медленнее, чем сложные перенаправление, я думал, что это было бы очевидно, но я предполагаю, что я должен описать его для всех (и я тоже закричал, что сообщение слишком раздуто, если я это сделаю в первую очередь) – osirisgothra 21 May 2015 в 12:55
  • 5
    Поскольку тайминг bar - все 0, я бы заподозрил, что оболочка не синхронизирует это правильно. Обратите внимание, что сообщение времени напечатано до , когда команда запущена? Эрго, он ничего не делает, а затем выполняет бар, так что вы вообще не измеряете бар. Сделайте что-то более сложное или большой цикл в баре, чтобы вы могли сделать более очевидным, что вы не синхронизируете ничего – Evan Langlois 21 December 2015 в 19:41

Функции практически всегда являются ответом, который уже достаточно внесен и подтвержден этой цитатой на странице руководства: «Для почти каждой цели псевдонимы заменяются функциями оболочки».

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

alias ssh_disc='ssh -O stop'

позволяет мне набирать smth like ssh_disc myhost, который расширяется, как ожидалось, как: ssh -O stop myhost

Это может быть полезно для команд, которые принимают сложные аргументы (моя память не то, что она использует t больше) ...

0
ответ дан sxc731 17 August 2018 в 08:55
поделиться

TL; DR: сделайте это вместо

. Его гораздо проще и читабельнее использовать функцию, чем псевдоним, чтобы поставить аргументы в середине команды.

$ wrap_args() { echo "before $@ after"; }
$ wrap_args 1 2 3
before 1 2 3 after

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

Уточнение

bash aliases do принимает аргументы, но только на end :

$ alias speak=echo
$ speak hello world
hello world

Ввод аргументов в средний команды через alias действительно возможен, но он становится уродливым.

Не пытайтесь это дома, детишки!

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

Обходной путь состоит в том, чтобы передать аргументы, которые alias принимает только в конце (g7) Решение 1

Если вы действительно против использования функции как таковой, вы можете использовать:

$ alias wrap_args='f(){ echo before "$@" after;  unset -f f; }; f'
$ wrap_args x y z
before x y z after

Вы можете заменить $@ на $1, если вам нужен только первый аргумент.

Объяснение 1

Это создает временную функцию f, которая передаются аргументы (обратите внимание, что f вызывается в самом конце). unset -f удаляет определение функции по мере того, как выполняется псевдоним, после чего он не зависает.

Решение 2

Вы также можете использовать подоболочку:

$ alias wrap_args='sh -c '\''echo before "$@" after'\'' _'

Пояснение 2

Псевдоним строит команду:

sh -c 'echo before "$@" after' _

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

  • Требуется заполнитель _ , но это может быть что угодно. Он устанавливается в sh $0 и требуется, чтобы первый из аргументов, заданных пользователем, не потреблялся. Демонстрация:
    sh -c 'echo Consumed: "$0" Printing: "$@"' alcohol drunken babble
    Consumed: alcohol Printing: drunken babble
    
  • Требуются одиночные кавычки внутри одиночных кавычек. Вот пример того, что он не работает с двойными кавычками:
    $ sh -c "echo Consumed: $0 Printing: $@" alcohol drunken babble
    Consumed: -bash Printing:
    
    Здесь значения интерактивной оболочки $0 и $@ заменены на двойные кавычки перед , которые передаются на sh. Вот доказательство:
    echo "Consumed: $0 Printing: $@"
    Consumed: -bash Printing:
    
    Одиночные кавычки гарантируют, что эти переменные не интерпретируются интерактивной оболочкой и передаются буквально в sh -c. Вы можете использовать двойные кавычки и \$@, но лучше всего привести свои аргументы (поскольку они могут содержать пробелы), а \"\$@\" выглядит еще более уродливым, но может помочь вам выиграть конкурс по запутыванию, где измотанные волосы являются предпосылкой для запись.
58
ответ дан Tom Hale 17 August 2018 в 08:55
поделиться
  • 1
    для решения 1 убедитесь, что вы используете одинарные кавычки, и избегайте \ & quot; вокруг $ @. Очень полезный метод, если вам это нужно. ти. – sgtz 27 June 2017 в 19:09
  • 2
    Решение 1 помогло мне обернуть rdesktop-vrdp аргументом для каждого сервера, который я хочу. – Hsehdar 4 May 2018 в 06:01
Другие вопросы по тегам:

Похожие вопросы: