Ordernar Variaveis

Fórum sobre a linguagem CA-Clipper.

Moderador: Moderadores

Avatar do usuário
Maligno
Membro Master
Membro Master
Mensagens: 6398
Registrado em: 06 Jul 2004 01:40
Localização: Londrina/PR

Mensagem por Maligno »

Código: Selecionar todos

nMax := 0
nMes := 0
Aeval(aMeses,{|n,i|nMax := if(n>nMax, (nMes:=i,n), nMax)})
O bloco de código de AEval contém dois argumentos. Você sabe que este bloco avalia (evalua, como dizem alguns) elemento por elemento da matriz informada. No nosso caso, n é o elemento que está sendo avaliado e i é o número de ordem desse elemento dentro da matriz.

Como o valor de nMax depende do retorno do IF(), ao testar a expressão n > nMax, e sendo TRUE, faço o IF() retornar n, mas só depois (e tem de ser depois) de atribuir o número deste mês (i) a nMes.

Se sua dúvida ficou na sub-expressão (nMes:=i,n), apesar de meio estranha e incomum, ela é perfeitamente válida. Mas tem um porém. Sem parênteses, é erro de sintaxe. Com parênteses é uma expressão múltipla normal que, avaliada, retornará o último valor apurado, após a última vírgula. No caso, n. Eu só aproveitei essa característica pra também fazer a atribuição de nMes. Uma carona. :)
[]'s
Maligno
---
Não respondo questões técnicas através de MP ou eMail. Não insista.
As dúvidas devem ser postadas no fórum. Desta forma, todos poderão
se beneficiar das respostas.

---
Se um dia precisar de uma transfusão de sangue você perceberá como
é importante a figura do doador. Procure o hemocentro de sua cidade e
se informe sobre a doação de sangue, plaquetas e medula óssea. Doe!
Avatar do usuário
Pablo César
Usuário Nível 7
Usuário Nível 7
Mensagens: 5312
Registrado em: 31 Mai 2006 10:22
Localização: Curitiba - Paraná

Mensagem por Pablo César »

Maligno escreveu:(evalua, como dizem alguns)
Eu por exemplo, hihihi
Maligno escreveu:Se sua dúvida ficou na sub-expressão (nMes:=i,n), apesar de meio estranha e incomum, ela é perfeitamente válida.
Sim é a esta expressão que ainda não consigo entender.
Maligno escreveu:retornará o último valor apurado, após a última vírgula. No caso, n.
E o i para que seria ? Quê valor tem ?
Maligno escreveu:Eu só aproveitei essa característica pra também fazer a atribuição de nMes. Uma carona. :)
Sim, isso entendí e eu ia sugerir acrescentar ao seu exemplo inicial, mas achei que eu ia me embanar todo.
Um clip-abraço !

Pablo César Arrascaeta
Compartilhe suas dúvidas e soluções com todos os colegas aqui do fórum.
Evite enviar as dúvidas técnicas por MPs ou eMails, assim todos iremos beneficiar-nos.
Adalberto
Usuário Nível 3
Usuário Nível 3
Mensagens: 343
Registrado em: 01 Set 2007 01:09
Localização: Santa Cruz de la Sierra - Bolivia

ordenar variaveis

Mensagem por Adalberto »

Pablo César.

Sua pergunta se refere a essa linha?

LOCAL nIndice := 1 , nI

Então podemos modificar assim:

LOCAL nIndice := 1 , nI := 0

E só uma variável do tipo numérica, eu utilizo a notação Ungara, onde a primeira letra em minúscula diz o tipo da variável, neste caso nI quer dize que I e uma numérica. Assim nMaior.

anValor é: a= array, n=Numérico, Valor=Nome da variável

Perdão se exagere na explicação, foi com o propósito de deixar tudo claro respeito de este modo de nomear a variável.

Abraços e paz para você.
Adalberto
Usuário Nível 3
Usuário Nível 3
Mensagens: 343
Registrado em: 01 Set 2007 01:09
Localização: Santa Cruz de la Sierra - Bolivia

ordenar variaveis

Mensagem por Adalberto »

Pablo César.

Por favor, não considere meu ultimo post, escrevi ele sem ler o post do maligno, foi um terrível descuido de minha parte, motivado pela conversação de minha mãe, com este filho seu que conversa e posta. ( já pedi perdão a minha mãe).

Perdoe Pablo César, e também perdão a todos os clippeiros do foro.
Avatar do usuário
Maligno
Membro Master
Membro Master
Mensagens: 6398
Registrado em: 06 Jul 2004 01:40
Localização: Londrina/PR

Mensagem por Maligno »

Pablo César escreveu:
Maligno escreveu:(evalua, como dizem alguns)
Eu por exemplo, hihihi
Não só você. A tradução de "evaluation" não é muito clara. Por isso há quem use a tradução "evaluar", que não está tão errada. E você está perdoado, pois em espanhol traduz-se como "evaluar" ou "avaluar". :)
Maligno escreveu:Se sua dúvida ficou na sub-expressão (nMes:=i,n), apesar de meio estranha e incomum, ela é perfeitamente válida.
Sim é a esta expressão que ainda não consigo entender.
É uma expressão múltipla. Um exemplo prático para entender melhor:

Código: Selecionar todos

x :=  1,2,3,4,5
y := (1,2,3,4,5)
Um programa assim não compilaria por culpa da atribuição de x. Isso é erro de sintaxe. Mas y está sendo atribuído certinho. Ele receberá o valor 5, pois expressões múltiplas sempre retornam o último valor avaliado.
E o i para que seria ? Quê valor tem ?
A variável i no bloco de código é o índice (número de ordem) do elemento que está sendo avaliado naquele momento. Se o valor deste elemento for maior que nMax, i será utilizado para indicar o número do mês onde esse valor aparece.
[]'s
Maligno
---
Não respondo questões técnicas através de MP ou eMail. Não insista.
As dúvidas devem ser postadas no fórum. Desta forma, todos poderão
se beneficiar das respostas.

---
Se um dia precisar de uma transfusão de sangue você perceberá como
é importante a figura do doador. Procure o hemocentro de sua cidade e
se informe sobre a doação de sangue, plaquetas e medula óssea. Doe!
Avatar do usuário
Pablo César
Usuário Nível 7
Usuário Nível 7
Mensagens: 5312
Registrado em: 31 Mai 2006 10:22
Localização: Curitiba - Paraná

Mensagem por Pablo César »

Entendí e gostei (you are a genius !). No seu exemplo:

Código: Selecionar todos

aMeses:={12.22,33.44,55.78,11.01,66.38,23.34}
nMax := 0 
nMes := 0 
Aeval(aMeses,{|n,i|nMax := if(n>nMax, (nMes:=i,n), nMax)})
Pode ser traduzida em:

Código: Selecionar todos

aMeses:={12.22,33.44,55.78,11.01,66.38,23.34}
n:=0
nMax:=0
nMes:=0
FOR i=1 TO LEN(aMeses)
    n:=aMeses[i]
    IF n>nMax
       nMax:=n
       nMes:=i
    ELSE
       nMax:=nMax
    ENDIF
NEXT
? nMes
? nMax
Interessante a questão (nMes:=i,n) dentro do IF() além de atribuir a variável nMes com i o n atribui a variável nMax da condição IF(). Entendí, essa sentença cumpre duas funções. Obrigado pelo ensinamento (your trully a expert), tks.
Um clip-abraço !

Pablo César Arrascaeta
Compartilhe suas dúvidas e soluções com todos os colegas aqui do fórum.
Evite enviar as dúvidas técnicas por MPs ou eMails, assim todos iremos beneficiar-nos.
Adalberto
Usuário Nível 3
Usuário Nível 3
Mensagens: 343
Registrado em: 01 Set 2007 01:09
Localização: Santa Cruz de la Sierra - Bolivia

ordenar variaveis

Mensagem por Adalberto »

Pablo César,

Em sua tradução: ¿que aconteceria se os valores todos foram negativos?.

Iria mostrar 0 (zero) como maior.
Avatar do usuário
Maligno
Membro Master
Membro Master
Mensagens: 6398
Registrado em: 06 Jul 2004 01:40
Localização: Londrina/PR

Mensagem por Maligno »

Mas zero é sempre maior que qualquer valor negativo, Adalberto. O único reparo que coloco no código do colega é que o ELSE do teste é desnecessário. Mas não tem tanto problema, já que é só um exemplo. Ele deve ter feito rápido e se distraiu.
[]'s
Maligno
---
Não respondo questões técnicas através de MP ou eMail. Não insista.
As dúvidas devem ser postadas no fórum. Desta forma, todos poderão
se beneficiar das respostas.

---
Se um dia precisar de uma transfusão de sangue você perceberá como
é importante a figura do doador. Procure o hemocentro de sua cidade e
se informe sobre a doação de sangue, plaquetas e medula óssea. Doe!
Avatar do usuário
Pablo César
Usuário Nível 7
Usuário Nível 7
Mensagens: 5312
Registrado em: 31 Mai 2006 10:22
Localização: Curitiba - Paraná

Re: ordenar variaveis

Mensagem por Pablo César »

Muito bem Adalberto, se todos os elementos forem negativos não iria funcionar direito (conforme meu exemplo anterior), mas veja o que fiz que funcionaria em ambos casos:

Código: Selecionar todos

aMeses:={-12.22,-33.44,-55.78,-11.01,-66.38,-23.34} // tudo negativo
tAllNeg:=.T.
FOR i=1 to LEN(aMeses)
    IF aMeses[i]>0
       tAllNeg:=.F.
    ENDIF
NEXT

nMax:=0
nMes:=0
FOR i=1 TO LEN(aMeses)
    IF tAllNeg
       n:=(aMeses[i])*-1
    ELSE
       n:=aMeses[i]
    ENDIF
    IF n>nMax
       nMax:=n
       nMes:=i
    ELSE
       nMax:=nMax
    ENDIF
NEXT
? nMes
? nMax
Agora com este exemplo, experimente asignando valores negativos e positivos mixtos ou até mesmo somente utdo positivo e funcionará normal. Agora cómo fazer tudo numa linha só, não sei se seria possível, quem sabe o mestre Maligno consiga...
O único reparo que coloco no código do colega é que o ELSE do teste é desnecessário. Mas não tem tanto problema, já que é só um exemplo. Ele deve ter feito rápido e se distraiu.
Com certeza o meu ELSE é desnecessário. Não foi distração minha, não. Eu apenas coloquei para evidenciar o seu exemplo no qual também é atribuido a si mesmo ...if(n>nMax, (nMes:=i,n), nMax)... Fiz isso para que o pessoal entendesse o que você tinha feito Maligno.
Um clip-abraço !

Pablo César Arrascaeta
Compartilhe suas dúvidas e soluções com todos os colegas aqui do fórum.
Evite enviar as dúvidas técnicas por MPs ou eMails, assim todos iremos beneficiar-nos.
Avatar do usuário
Maligno
Membro Master
Membro Master
Mensagens: 6398
Registrado em: 06 Jul 2004 01:40
Localização: Londrina/PR

Mensagem por Maligno »

Agora cómo fazer tudo numa linha só, não sei se seria possível
É só seguir o raciocínio de antes:

Código: Selecionar todos

for i := 1 to Len(aMeses)
   nMax := if((n:=aMeses[i]*if(tAllNeg,-1,1))>nMax,(nMes:=i,n)
next
Só não entendo porque mudar o sinal do valor, se a proposta é descobrir qual o maior valor. Se todos forem negativos e o problema for o zero inicial, é só iniciar nMax com um valor impossível. Algo do tipo -999999.

Usar o flag tAllNeg para indicar que há apenas valores negativos só para inverter os valores dos elementos não ajuda muito, porque se todos forem negativos, você inverte seus sinais, mas aí a busca deve se inverter também. Você precisará descobrir qual o menor valor. Valor este que, originalmente negativo, será o maior. :)
[]'s
Maligno
---
Não respondo questões técnicas através de MP ou eMail. Não insista.
As dúvidas devem ser postadas no fórum. Desta forma, todos poderão
se beneficiar das respostas.

---
Se um dia precisar de uma transfusão de sangue você perceberá como
é importante a figura do doador. Procure o hemocentro de sua cidade e
se informe sobre a doação de sangue, plaquetas e medula óssea. Doe!
Avatar do usuário
Pablo César
Usuário Nível 7
Usuário Nível 7
Mensagens: 5312
Registrado em: 31 Mai 2006 10:22
Localização: Curitiba - Paraná

Mensagem por Pablo César »

Quanto ao seu código: Beleza, funcionou corrigindo para:

Código: Selecionar todos

for i := 1 to Len(aMeses)
    nMax := if( (n:=aMeses[i]*if(tAllNeg,-1,1))>nMax,(nMes:=i,n), nMax )
next
Só não entendo porque mudar o sinal do valor, se a proposta é descobrir qual o maior valor. Se todos forem negativos e o problema for o zero inicial, é só iniciar nMax com um valor impossível. Algo do tipo -999999
Pois é, eu fiz isso e ainda achei que o resultado estava ERRADO. Mas eu me enganei e concordo contigo que não haveria necessidade de converter sinal, ora porquê ? Porque o resultado de todos os elementos negativos, será o maior aquele que for mais próximo do ZERO e convertendo este resultado muda o critério. Portanto apresento a versão corrigida:

Código: Selecionar todos

aMeses:={-12.22,-33.44,-55.78,-11.01,-66.38,-23.34}
nMax:=aMeses[1] // Corrigido conforme sugirido por Adalberto/Maligno
nMes:=0
FOR i=1 TO LEN(aMeses)
    n:=aMeses[i]
    IF n>nMax
       nMax:=n
       nMes:=i
    ENDIF
NEXT
? nMes
? nMax
ou no seu modo sintético:

Código: Selecionar todos

aMeses:={-12.22,-33.44,-55.78,-11.01,-66.38,-23.34}
nMax:=aMeses[1] // Corrigido conforme sugirido por Adalberto/Maligno
nMes:=0
Aeval(aMeses,{|n,i|nMax := if(n>nMax, (nMes:=i,n), nMax)})
? nMes
? nMax
Então podemos esquecer a razão de converter os elementos que estão como números negativos. Valeu Maligno pelo esclarecimento.

Obs.: Desculpe Maligno não ter respondido no chat, não te ví porque eu estava no Prompt de comando ocupado com os testes do número negativo e como o chat não possue recurso de avisar usuário quando está em outra sessão: acabei perdendo a oportunidade de dialogar contigo. E também não estavam ligadas as caixas de som. Sorry.
Editado pela última vez por Pablo César em 13 Fev 2008 13:13, em um total de 2 vezes.
Um clip-abraço !

Pablo César Arrascaeta
Compartilhe suas dúvidas e soluções com todos os colegas aqui do fórum.
Evite enviar as dúvidas técnicas por MPs ou eMails, assim todos iremos beneficiar-nos.
Avatar do usuário
Maligno
Membro Master
Membro Master
Mensagens: 6398
Registrado em: 06 Jul 2004 01:40
Localização: Londrina/PR

Mensagem por Maligno »

Pablo César escreveu:Quanto ao seu código: Beleza, funcionou corrigindo para:
Pois é. Esqueci da última parte. Mas numa linha só acabou virando uma salada. :))) Ainda bem que é só por curiosidade mesmo.
[]'s
Maligno
---
Não respondo questões técnicas através de MP ou eMail. Não insista.
As dúvidas devem ser postadas no fórum. Desta forma, todos poderão
se beneficiar das respostas.

---
Se um dia precisar de uma transfusão de sangue você perceberá como
é importante a figura do doador. Procure o hemocentro de sua cidade e
se informe sobre a doação de sangue, plaquetas e medula óssea. Doe!
marcos.gurupi
Usuário Nível 4
Usuário Nível 4
Mensagens: 939
Registrado em: 06 Jul 2004 11:53
Localização: Gurupi-TO

Mensagem por marcos.gurupi »

Kros colegas, obrigado a todos pelas dicas foi resolvido com o mesmo exemplo do Maligno.

Marcos Roberto.
Adalberto
Usuário Nível 3
Usuário Nível 3
Mensagens: 343
Registrado em: 01 Set 2007 01:09
Localização: Santa Cruz de la Sierra - Bolivia

ordenar variaveis

Mensagem por Adalberto »

Pablo César,

Só com animo de contribuir.

Meu exemplo roda certinho encontra o valor maior sejam quaisquer tipos de valores, só negativos, positivos o misturado, e não precisa de esse valor -9999999.
Avatar do usuário
Maligno
Membro Master
Membro Master
Mensagens: 6398
Registrado em: 06 Jul 2004 01:40
Localização: Londrina/PR

Mensagem por Maligno »

Justamente, Adalberto. O valor inicial -999999 sugerido também pode ser substituído pelo valor do primeiro elemento. Tanto o custo quanto efeito são os mesmos.
[]'s
Maligno
---
Não respondo questões técnicas através de MP ou eMail. Não insista.
As dúvidas devem ser postadas no fórum. Desta forma, todos poderão
se beneficiar das respostas.

---
Se um dia precisar de uma transfusão de sangue você perceberá como
é importante a figura do doador. Procure o hemocentro de sua cidade e
se informe sobre a doação de sangue, plaquetas e medula óssea. Doe!
Responder