AskOverflow.Dev

AskOverflow.Dev Logo AskOverflow.Dev Logo

AskOverflow.Dev Navigation

  • Início
  • system&network
  • Ubuntu
  • Unix
  • DBA
  • Computer
  • Coding
  • LangChain

Mobile menu

Close
  • Início
  • system&network
    • Recentes
    • Highest score
    • tags
  • Ubuntu
    • Recentes
    • Highest score
    • tags
  • Unix
    • Recentes
    • tags
  • DBA
    • Recentes
    • tags
  • Computer
    • Recentes
    • tags
  • Coding
    • Recentes
    • tags
Início / unix / Perguntas / 532096
Accepted
KuboMD
KuboMD
Asked: 2019-07-26 05:54:19 +0800 CST2019-07-26 05:54:19 +0800 CST 2019-07-26 05:54:19 +0800 CST

Associação Array não está sendo redeclarado?

  • 772

Eu tenho um programa que funciona como um menu. Ele tem uma matriz associativa chamada configcomo:

declare -A config=( [h]="?" [c]="?" [x]="?" [l]="?" [t]="?" [n]="?" )

No loop principal há uma verificação para ver se todos os valores foram configurados, como:

if [ "${config[h]}" == "Y" ] && [ "${config[c]}" == "Y" ] && [ "${config[l]}" == "Y" ] && [ "${config[x]}" == "Y" ] && [ "${config[t]}" == "Y" ] && [ "${config[n]}" == "Y" ];

Agora, quando termino uma execução, desmarco e redeclaro a matriz.

unset config; declare -A config=( [h]="?" [c]="?" [x]="?" [l]="?" [t]="?" [n]="?" )

No entanto, a matriz não parece ser declarada novamente corretamente. Isso porque quando configuro apenas um dos valores, [C]=Ypor exemplo, a ifinstrução passa. Eu tenho certeza que sim porque o corpo da ifinstrução muda parte da cor do texto. Eu acredito que é porque o resto dos índices não são realmente set="?", então a ifdeclaração é reduzida para apenas [ "${config[c]}" == "Y"]which is be true. Eu sei disso desde quando eu ecoo $config[@]dentro do corpo da ifdeclaração, com certeza eu só vejo um "Y" em vez de cinco. Como faço para que o array redeclare corretamente?

EDIT
Obrigado pela atenção;

  1. Os valores são definidos como Y após alguma entrada do usuário. Esta parte eu estou muito confiante e, portanto, omitida da minha pergunta. Todos seguem este formato:

     read ch
            if [ $ch == "Hosts" ]; then
                    while true; do
                            nano listHosts
                            echo -en "Commit this list of Hostnames? [Y|N to re-edit]: "
                            read yn
                            if [ $yn == "Y" ] || [ $yn == "y" ] || [ $yn == "yes" ]; then
                                    break
                            elif [ $yn == "N" ] || [ $yn == "n" ] || [ $yn == "no" ]; then  
                                    continue
                            fi      
                    done
                    config[h]="Y"
    
  2. Em relação ao comentário de Kusalanda, verifiquei se há letras incorretas, mas é consistentemente 'c' minúsculo. Bem, sim, eu quis dizer ${config[@]}.

  3. Declare -p lança alguma luz: declare -a config='([0]="Y")'

Como é que -p diz que usei a minúscula? As chamadas estão nesta ordem:

 unset config
 declare -A config=( [h]="?" [c]="?" [x]="?" [l]="?" [t]="?" [n]="?" )   

Então eu defino $ch="Commands" via read;

 elif [ $ch == "Commands" ]; then  
                while true; do
                        nano iSet
                        echo -en "Commit this list of commands? [Y|N to re-edit]: "             
                        read yn                        
                        if [ $yn == "Y" ] || [ $yn == "y" ] || [ $yn == "yes" ]; then           
                                break
                        elif [ $yn == "N" ] || [ $yn == "n" ] || [ $yn == "no" ]; then                  
                                continue        
                        fi      
                done        
                config[c]="Y"
                declare -p config

Tentei recriar em um script menor conforme a sugestão do Bodo:

dec() {
        declare -A config=( [h]="?", [c]="?" )
}
test() {
        declare -p config
        if [ "${config[h]}" == "Y" ] && [ "${config[c]}" == "Y" ]; then 
                echo "Yup"
        fi
}

dec
config[h]="Y"; config[c]="Y"

unset config
dec
config[h]="Y" 

test

E assim como no meu outro script, a ifresolução é verdadeira: declare -a config='([0]="Y")' Yup

bash array
  • 1 1 respostas
  • 137 Views

1 respostas

  • Voted
  1. Best Answer
    Bodo
    2019-07-26T07:00:52+08:002019-07-26T07:00:52+08:00

    Você precisa declarar a matriz como global em suas funções usando declare -g .... Caso contrário, o array será uma variável local na função . Consulte https://unix.stackexchange.com/a/136721/330217

    Veja este script modificado com alguma saída de depuração

    #! /bin/bash
    
    # set -x
    
    dec() {
            # declare -A config=( [h]="?", [c]="?" )
            declare -gA config=( [h]="?" [c]="?" )
            echo dec: ${config[*]}
    }
    test() {
            declare -p config
            if [ "${config[h]}" == "Y" ] && [ "${config[c]}" == "Y" ]; then
                    echo "Yup"
            else
                    echo "No"
            fi
            echo test: ${config[*]}
    }
    
    dec
    echo 1: ${config[*]}
    config[h]="Y"; config[c]="Y"
    echo 2: ${config[*]}
    
    test
    
    unset config
    dec
    echo 3: ${config[*]}
    config[h]="Y"
    echo 4: ${config[*]}
    
    test
    

    A saída é

    $ ./script
    dec: ? ?
    1: ? ?
    2: Y Y
    declare -A config=([c]="Y" [h]="Y" )
    Yup
    test: Y Y
    dec: ? ?
    3: ? ?
    4: ? Y
    declare -A config=([c]="?" [h]="Y" )
    No
    test: ? Y
    

    Quando eu descomento sua linha e comento minha linha modificada, a saída é

    $ ./script
    dec: ? ?,
    1:
    2: Y
    declare -a config=([0]="Y")
    Yup
    test: Y
    dec: ? ?,
    3:
    4: Y
    declare -a config=([0]="Y")
    Yup
    test: Y
    

    Copiado do comentário de @ilkkachu:

    E claro, depois que a declaração local do array associativo sai do escopo, a atribuição config[h]="Y"cria um array regular, onde o índice é interpretado em um contexto aritmético, onde h(recursivamente) expande o valor da variável h, o que provavelmente não é set e você obtém a string vazia que é avaliada como zero, então é isso config[0]que é definido. E não há mensagem de erro, pois set -unão está em vigor.

    Isso pode ser visto na saída declare -a config=([0]="Y")do script original.

    • 2

relate perguntas

  • exportar variáveis ​​​​env programaticamente, via stdout do comando [duplicado]

  • Problema estranho ao passar variáveis ​​do arquivo de texto

  • Enquanto a linha lê mantendo os espaços de escape?

  • ordem de substituição de processos `te` e `bash`

  • Execute um script muito lento até que seja bem-sucedido

Sidebar

Stats

  • Perguntas 205573
  • respostas 270741
  • best respostas 135370
  • utilizador 68524
  • Highest score
  • respostas
  • Marko Smith

    Possível firmware ausente /lib/firmware/i915/* para o módulo i915

    • 3 respostas
  • Marko Smith

    Falha ao buscar o repositório de backports jessie

    • 4 respostas
  • Marko Smith

    Como exportar uma chave privada GPG e uma chave pública para um arquivo

    • 4 respostas
  • Marko Smith

    Como podemos executar um comando armazenado em uma variável?

    • 5 respostas
  • Marko Smith

    Como configurar o systemd-resolved e o systemd-networkd para usar o servidor DNS local para resolver domínios locais e o servidor DNS remoto para domínios remotos?

    • 3 respostas
  • Marko Smith

    apt-get update error no Kali Linux após a atualização do dist [duplicado]

    • 2 respostas
  • Marko Smith

    Como ver as últimas linhas x do log de serviço systemctl

    • 5 respostas
  • Marko Smith

    Nano - pule para o final do arquivo

    • 8 respostas
  • Marko Smith

    erro grub: você precisa carregar o kernel primeiro

    • 4 respostas
  • Marko Smith

    Como baixar o pacote não instalá-lo com o comando apt-get?

    • 7 respostas
  • Martin Hope
    user12345 Falha ao buscar o repositório de backports jessie 2019-03-27 04:39:28 +0800 CST
  • Martin Hope
    Carl Por que a maioria dos exemplos do systemd contém WantedBy=multi-user.target? 2019-03-15 11:49:25 +0800 CST
  • Martin Hope
    rocky Como exportar uma chave privada GPG e uma chave pública para um arquivo 2018-11-16 05:36:15 +0800 CST
  • Martin Hope
    Evan Carroll status systemctl mostra: "Estado: degradado" 2018-06-03 18:48:17 +0800 CST
  • Martin Hope
    Tim Como podemos executar um comando armazenado em uma variável? 2018-05-21 04:46:29 +0800 CST
  • Martin Hope
    Ankur S Por que /dev/null é um arquivo? Por que sua função não é implementada como um programa simples? 2018-04-17 07:28:04 +0800 CST
  • Martin Hope
    user3191334 Como ver as últimas linhas x do log de serviço systemctl 2018-02-07 00:14:16 +0800 CST
  • Martin Hope
    Marko Pacak Nano - pule para o final do arquivo 2018-02-01 01:53:03 +0800 CST
  • Martin Hope
    Kidburla Por que verdadeiro e falso são tão grandes? 2018-01-26 12:14:47 +0800 CST
  • Martin Hope
    Christos Baziotis Substitua a string em um arquivo de texto enorme (70 GB), uma linha 2017-12-30 06:58:33 +0800 CST

Hot tag

linux bash debian shell-script text-processing ubuntu centos shell awk ssh

Explore

  • Início
  • Perguntas
    • Recentes
    • Highest score
  • tag
  • help

Footer

AskOverflow.Dev

About Us

  • About Us
  • Contact Us

Legal Stuff

  • Privacy Policy

Language

  • Pt
  • Server
  • Unix

© 2023 AskOverflow.DEV All Rights Reserve