Schell script - laço for - números grandes

1. Schell script - laço for - números grandes

Fabio Bairros
fdabairros

(usa Ubuntu)

Enviado em 21/10/2022 - 17:54h

Saudações.

Estou usando um laço for em um arquivo .sh que chama um programa em Python e passa valores gerados no laço.
No entanto para valores de 1e18 e superiores parece que o laço não executa ou não passa os valores corretamente.
Há alguma maneira de corrigir isto ? E prosseguir passando números desta ordem e superiores ?



Agradeço desde já a atenção,
Fábio


  


2. Re: Schell script - laço for - números grandes

Marcelo Oliver
msoliver

(usa Debian)

Enviado em 21/10/2022 - 20:36h


fdabairros escreveu:

Saudações.

Estou usando um laço for em um arquivo .sh que chama um programa em Python e passa valores gerados no laço.
No entanto para valores de 1e18 e superiores parece que o laço não executa ou não passa os valores corretamente.
Há alguma maneira de corrigir isto ? E prosseguir passando números desta ordem e superiores ?



Agradeço desde já a atenção,
Fábio

Boa noite Fábio,
afinal.....
É shell script ou C++?
Se "SHELL", poste o script, é mais fácil para te ajudar....
------------------------------------------------------------------------------
Exemplos em Bash:
for ((n=0;n<10;++n));do
echo "$n"
done

------------------------------------------------------------------------------
Simplificado:
for ((n=0;n<10;n++)) { echo "$n";} 

------------------------------------------------------------------------------
While:
n=0;
while (($n<10));do
echo "$n";let n++;
done

______________________________________________________________________
Att.: Marcelo Oliver
______________________________________________________________________



3. Re: Schell script - laço for - números grandes

Fabio Bairros
fdabairros

(usa Ubuntu)

Enviado em 26/10/2022 - 08:35h


msoliver escreveu:


fdabairros escreveu:

Saudações.

Estou usando um laço for em um arquivo .sh que chama um programa em Python e passa valores gerados no laço.
No entanto para valores de 1e18 e superiores parece que o laço não executa ou não passa os valores corretamente.
Há alguma maneira de corrigir isto ? E prosseguir passando números desta ordem e superiores ?



Agradeço desde já a atenção,
Fábio

Boa noite Fábio,
afinal.....
É shell script ou C++?
Se "SHELL", poste o script, é mais fácil para te ajudar....
------------------------------------------------------------------------------
Exemplos em Bash:
for ((n=0;n<10;++n));do
echo "$n"
done

------------------------------------------------------------------------------
Simplificado:
for ((n=0;n<10;n++)) { echo "$n";} 

------------------------------------------------------------------------------
While:
n=0;
while (($n<10));do
echo "$n";let n++;
done

______________________________________________________________________
Att.: Marcelo Oliver
______________________________________________________________________


Agradeço o retorno, Marcelo.

Segue abaixo um trecho do script.

for indice in {1000000000000000000..1000000000000000000000..50000000000000000000}; do # valores na ordem de 1E18 e 1E21


#python3 teste.py $indice

done


att,
Fábio










4. Re: Schell script - laço for - números grandes

Marcelo Oliver
msoliver

(usa Debian)

Enviado em 27/10/2022 - 14:59h


fdabairros escreveu:


msoliver escreveu:


fdabairros escreveu:

Saudações.

Estou usando um laço for em um arquivo .sh que chama um programa em Python e passa valores gerados no laço.
No entanto para valores de 1e18 e superiores parece que o laço não executa ou não passa os valores corretamente.
Há alguma maneira de corrigir isto ? E prosseguir passando números desta ordem e superiores ?



Agradeço desde já a atenção,
Fábio

Boa noite Fábio,
afinal.....
É shell script ou C++?
Se "SHELL", poste o script, é mais fácil para te ajudar....
------------------------------------------------------------------------------
Exemplos em Bash:
for ((n=0;n<10;++n));do
echo "$n"
done

------------------------------------------------------------------------------
Simplificado:
for ((n=0;n<10;n++)) { echo "$n";} 

------------------------------------------------------------------------------
While:
n=0;
while (($n<10));do
echo "$n";let n++;
done

______________________________________________________________________
Att.: Marcelo Oliver
______________________________________________________________________


Agradeço o retorno, Marcelo.

Segue abaixo um trecho do script.

for indice in {1000000000000000000..1000000000000000000000..50000000000000000000}; do # valores na ordem de 1E18 e 1E21


#python3 teste.py $indice

done


att,
Fábio

Boa tarde fdabairros.
Não tinha observado o detalhe: # valores na ordem de 1E18 e 1E21
O bash, sh e zsh NÃO trabalham com essa "grandeza", veja abaixo, testes com o bash:
Erro na soma, a partir da linha 19:
for ((n=0;n<=21;n++)) {  
z=$(printf '%*s' $n);
z=${z// /0};
sbash=$((10+1${z}));
sbc=$(bc <<< "10+1${z}");
[[ "${sbash}" == "${sbc}" ]] && stt="Certo" || stt="Errado";
printf "%02d => %s = %d %s\n" $n "10 + 1${z}" $sbash $stt;
}


00 => 10 + 1 = 11 Certo
01 => 10 + 10 = 20 Certo
02 => 10 + 100 = 110 Certo
03 => 10 + 1000 = 1010 Certo
04 => 10 + 10000 = 10010 Certo
05 => 10 + 100000 = 100010 Certo
06 => 10 + 1000000 = 1000010 Certo
07 => 10 + 10000000 = 10000010 Certo
08 => 10 + 100000000 = 100000010 Certo
09 => 10 + 1000000000 = 1000000010 Certo
10 => 10 + 10000000000 = 10000000010 Certo
11 => 10 + 100000000000 = 100000000010 Certo
12 => 10 + 1000000000000 = 1000000000010 Certo
13 => 10 + 10000000000000 = 10000000000010 Certo
14 => 10 + 100000000000000 = 100000000000010 Certo
15 => 10 + 1000000000000000 = 1000000000000010 Certo
16 => 10 + 10000000000000000 = 10000000000000010 Certo
17 => 10 + 100000000000000000 = 100000000000000010 Certo
18 => 10 + 1000000000000000000 = 1000000000000000010 Certo
19 => 10 + 10000000000000000000 = -8446744073709551606 Errado
20 => 10 + 100000000000000000000 = 7766279631452241930 Errado
21 => 10 + 1000000000000000000000 = 3875820019684212746 Errado
----------------------------------------------------------------------------------------------------------------
Opcão:
bc <<< "10 + 1000000000000000000000"
----------------------------------------------------------------------------------------------------------------
z='000000000000000000'
echo ${#z}
18
bc <<< "1${z} + 50${z}000"
50001000000000000000000
bc <<< "1${z} + 50${z}000000"
50000001000000000000000000
bc <<< "1${z}000 + 5000${z}000000"
5000001000000000000000000000
----------------------------------------------------------------------------------------------------------------

É isso...
______________________________________________________________________
Importante:
lynx --dump https://www.vivaolinux.com.br/termos-de-uso/ | sed -nr '/^[ ]+Se/,/dou.$/p'
______________________________________________________________________
Nota de esclarecimento:
O comando: ACIMA, faz parte da minha assinatura.
Att.: Marcelo Oliver
______________________________________________________________________



5. Re: Schell script - laço for - números grandes

Paulo
paulo1205

(usa Ubuntu)

Enviado em 29/10/2022 - 04:57h

fdabairros escreveu:

Agradeço o retorno, Marcelo.

Segue abaixo um trecho do script.

for indice in {1000000000000000000..1000000000000000000000..50000000000000000000}; do	# valores na ordem de 1E18 e 1E21


#python3 teste.py $indice

done


O problema é que essa geração de valores incrementais na forma {limite_inferior..limite_superior} é um recurso do shell que utiliza aritmética de valores inteiros. Num PC de 64 bits, como os nossos PCs de uns quinze anos para cá, a representação de valores inteiros em 64 bits permite contar de -2^63 (-9223372036854775808, que é aproximadamente -10^(18,6489)) até +(2^63)-1 (9223372036854775807), ou, se não forem usados números negativos, de 0 até (2^64)-1 (18446744073709551615, cerca de 10^(19,2659)).

Para usar valores fora dessa faixa, um programa ou linguagem de programação tem de usar uma técnica de representação de big numbers, que consiste em usar múltiplas unidades de memória (quer sejam caracteres, bytes, valores de 64, 32 ou 16 bits, etc.) para representar partes do número, e realizar operações aritméticas com cada uma dessas partes individualmente (dependendo da operação), mas de uma forma que, na hora de exibir (ou de ler) o número completo, as diferentes partes são justapostas de modo adequado a representar o número inteiro.

Tal forma de trabalhar, por sinal, reflete a forma como a maioria de nós lida com números compostos por múltiplos algarismos. Lembra de quando a gente estudou, lá pela quarta série, sobre notação numérica posicional com um conjunto de algarismos fixos, e sobre unidade, dezena e centena, e sobre a classe simples, classe dos milhares, classe dos milhões etc.? Graças a propriedades de distributividade, associatividade, comutatividade das operações aritméticas, nós conseguimos trabalhar com números de múltiplos algarismos dividindo-os em blocos. Pois é: dá para programar o computador para “pensar” e realizar operações aritméticas do mesmo modo que nós.

O problema é que, quando comparadas com as operações usando a representação nativa do processador, operações com big numbers tendem a ser muito mais lentas. Somando-se essa lentidão ao fato de que é raro ter de usar, no dia-a-dia da maioria das pessoas valores que, ao mesmo tempo, sejam muito grandes e necessitem de uma precisão unitária (ou fracionária) muito grande (o que é uma simples unidade, perto de 18 quintilhões?), o uso de big numbers não é extremamente difundido entre as linguagens de programação e ferramentas comuns.

Sendo esta uma comunidade de C e C++, cumpre observar que nenhuma dessas duas linguagens define uma representação obrigatória de big numbers. Para tais linguagens, o uso de big numbers é possível através de bibliotecas externas, e é possível que diferentes bibliotecas usem diferentes representações internas e operações válidas, não necessariamente compatível com outras implementações.


Você mencionou Python. Se não me engano, Python é umas das linguagens que usam big numbers nativamente. Outro colega nosso, ao longo desta discussão, mencionou a calculadora de precisão arbitrária — feita, portanto, com o propósito específico de não ficar limitada à precisão da máquina hospedeira — bc, que é uma ferramenta tradicional em sistemas UNIX.

O trecho de script que você mostrou tentaria usar o shell para criar argumentos a serem passados para um programa em Python, executado dentro de um laço de repetição, uma vez a cada iteração. Uma vez que o Python tem big numbers e o shell não, você poderia considerar mover o laço de repetição para dentro do programa em Python que, de outro modo, seria executado pelo seu script.


Depois dessa explicação toda, no seu script, você está querendo contar de um quintilhão até um sextilhão em incrementos de 50 quintilhões. Por que você não corta dezoito zeros de cada um desses números, e faz um laço de repetição de um até mil em incrementos de cinquenta, e multiplica (ou, na verdade, concatena dezoito zeros) ao valor do contador na hora de usá-lo como argumento do que quer que você venha a chamar? (Note que essa sugestão final é um exemplo de como a gente pode facilitar a nossa vida pensando em termos de unidade, dezenas, centenas e de diferentes classes.)


... Então Jesus afirmou de novo: “(...) eu vim para que tenham vida, e a tenham plenamente.” (João 10:7-10)


6. Re: Schell script - laço for - números grandes

Gerald pennington
Geraldpennington

(usa Kali)

Enviado em 29/10/2022 - 06:27h

To fix this problem use expression bash for loops syntax which share a common heritage with the C programming language. It is characterized by a three-parameter loop control expression; consisting of an initializer, a loop-test or condition, and a counting expression. https://www.tellculvers.onl/








Patrocínio

Site hospedado pelo provedor RedeHost.
Linux banner

Destaques

Artigos

Dicas

Tópicos

Top 10 do mês

Scripts