Página 1 de 1
criar expressão para Ascan
Enviado: 07 Nov 2018 13:53
por Mau_S
Ola Pessoal, meu primeiro post e estou precisando de uma ajuda para criar uma expressão para um array usando o Ascan e assim retornar a posição da informação dentro de um Array.
Segue o exemplo
_aDados := {}
AADD(_aDados,{"Produto","Descricao","00034001","00024401","00325801"})
Assim dentro do Array _aDados eu vou ter
_aDados[1][1] Produto
_aDados[1][2] Descricao
_aDados[1][3] 00034001
_aDados[1][4] 00024401
_aDados[1][5] 00325801
Numa condição que me meu codigo de um fornecedor é o abaixo atribuido a variavel _cFor, aonde o _cFor vai variar de conteudo dentro dos tres codigos acima
_cFor := "00024401"
Como seria a expressão para identificar a posição do conteudo _cFor dentro desse array. Eu sei que nesse exemplo fixo o _cFor que eu citei vai estar sempre na
posição 4, mas esse array do exemplo vai ser dinamico, ou seja, os codigos dentro dele vai sempre variar. Eu vou zera-lo e alimenta-lo a cada looping do meu programa
Vou retornar a posição na variavel _nPos
_nPos := Ascan(_aDados,{|x|x[01] == _cfor})
No caso acima esta errado retorna sempre 0 e eu não sei como montar a expressão de forma correta para retornar a posição correta do codigo.
Agradeço a ajuda
obrigado
criar expressão para Ascan
Enviado: 07 Nov 2018 14:58
por Mau_S
Obrigado, mas não funcionou.
No meu exemplo o Ascan deveria retornar a posição 4(_aDados[1][4]) aonde se encontra o conteudo "00024401" e mesmo montando a expressão conforme seu exemplo ele retorna posição 0
criar expressão para Ascan
Enviado: 07 Nov 2018 16:30
por Mau_S
Cara, muito obrigado por essa idéia, mas nem vai ser preciso tanto.
vendo o seu codigo de como voce tratou o aDados eu vi o meu erro. O meu ascan não funcionou porque ao inves de passar o _aDados como eu fiz eu devo passar
Ascan(_aDados[1],...... porque é a primeira "linha" do array somente.
Muitissimo obrigado :{
criar expressão para Ascan
Enviado: 07 Nov 2018 18:25
por JoséQuintas
Que conversa mais doida.
Se quer comparar o elemento 4, coloca 4 e não 1.
Código: Selecionar todos
nPos := AScan( aDados, { | x | x[ 4 ] == cFor } )
IF nPos != 0
? aDados[ nPos, 1 ]
? aDados[ nPos, 2 ]
? aDados( nPos, 3 ]
? aDados[ nPos, 4 ]
? aDados[ nPos, 5 ]
ENDIF
criar expressão para Ascan
Enviado: 07 Nov 2018 18:29
por JoséQuintas
E se quer comparar os elementos 3, 4 e 5, coloca 3, 4, e 5
Código: Selecionar todos
nPos := AScan( aDados, { | x | x[ 3 ] == cFor .OR. x[ 4 ] == cFor .OR. x[ 5 ] == cFor } )
criar expressão para Ascan
Enviado: 05 Mai 2021 11:32
por juniorcamilo
JoséQuintas escreveu:E se quer comparar os elementos 3, 4 e 5, coloca 3, 4, e 5
Código: Selecionar todos
nPos := AScan( aDados, { | x | x[ 3 ] == cFor .OR. x[ 4 ] == cFor .OR. x[ 5 ] == cFor } )
bom dia José Quintas!
como eu faria uma ascan com expressão para saber se dentro de uma matriz tem conteúdo, ou seja, c em uma posição da matriz não esta em branco?
criar expressão para Ascan
Enviado: 05 Mai 2021 12:38
por JoséQuintas
Acabo de pensar numa alternativa sobre como decidir isso.
Já comentei antes: codeblock é como função sem nome.
Pense numa função pra isso e coloque igual no codeblock.
Pensando no FOR/NEXT
Código: Selecionar todos
FOR nCont = 1 TO Len( aDados )
e := aDados[ nCont ]
Compara( e )
NEXT
Pensando no FOR/EACH
A função:
Isso acima em codeblock, retira o nome da função e o conteúdo é o próprio return.
FUNCTION Compara( e ) foi convertido pra | e |
e o RETURN e[ 1 ] < e[ 2 ] foi convertido pra e[ 1 ] < e[ 2 ]
O resultado de ASCAN() vai ser o primeiro que retornar verdadeiro, a posição dele.
Esse "não está em branco", ficou confuso se é combinado com o anterior, ou apenas ver se está em branco, ou ver se um ou todos estão em branco, etc.
Dependendo do que está querendo, por ser assim com .AND., ou com .OR., ou outra coisa
Código: Selecionar todos
Empty( e[ 3 ] ) .AND. Empty( e[ 4 ] ) .AND. Empty( e[ 5 ] )
criar expressão para Ascan
Enviado: 05 Mai 2021 12:40
por JoséQuintas
Ok, vi depois que é no fórum Clipper, o exemplo de FOR/EACH não vale pra Clipper, só pra Harbour, mas já fica sabendo que existe a opção.
criar expressão para Ascan
Enviado: 06 Mai 2021 07:45
por juniorcamilo
JoséQuintas escreveu:
Esse "não está em branco", ficou confuso se é combinado com o anterior, ou apenas ver se está em branco, ou ver se um ou todos estão em branco, etc.
EMPTY() MESMO, ou seja, exemplo basico!
Código: Selecionar todos
...
aMatriz := {{},{},{},{}}
for nCont = 1 to Len(aMatriz[1])
if !empty(Matriz[3,nCont])
exit
endif
next
....
como ficaria isso no ascan? sei q esta no forum de clipper! mas pode apresentar se necessário também para xharbour!
desde ja agradeço pela atenção!
criar expressão para Ascan
Enviado: 06 Mai 2021 12:09
por JoséQuintas
Código: Selecionar todos
...
aMatriz := {{},{},{},{}}
for nCont = 1 to Len(aMatriz[1])
if !empty(Matriz[3,nCont])
exit
endif
next
....
Tentar entender.... porque acho que o FOR/NEXT tá errado, talvez só a inversão 3,nCont, pra nCont,3 ou talvez mais que isso.
A impressão que tenho é que está querendo ver os arrays de dentro e não o array de fora.
Código: Selecionar todos
FOR nCont = 1 TO Len( aMatriz )
Funcao( aMatriz[ 1 ] ) // processa um elemento por vez, que tem 4 arrays
NEXT
...
FUNCTION Funcao( e )
FOR nCont = 1 TO Len( e[ 1 ] )
IF ! Empty( e[ 3 ] ) // olha se no array 3, a mesma posição do 1 está vazia
EXIT
ENDIF
NEXT
...
RETURN Nil
criar expressão para Ascan
Enviado: 06 Mai 2021 12:19
por JoséQuintas
Código: Selecionar todos
...
aMatriz := {{},{},{},{}}
for nCont = 1 to Len(aMatriz[1])
if !empty(Matriz[3,nCont])
exit
endif
next
....
Ok, ainda tentando entender...
Parece que pega da matriz 1, se na matriz 3 não estiver vazio.
Código: Selecionar todos
nPos := hb_AScan( aMatriz[ 3 ], { | e | ! Empty( e ) } )
? aMatriz[ 1 ][ nPos ]
criar expressão para Ascan
Enviado: 06 Mai 2021 12:24
por JoséQuintas
Ou pra simplificar, ainda tentando entender...
{ aLista1, aLista2, aLista3, aLista4 }, onde cada um é um array
Código: Selecionar todos
aMatriz := { {}, {}, {}, {} }
aLista1 := aMatriz[ 1 ]
aLista2 := aMatriz[ 2 ]
aLista3 := aMatriz[ 3 ]
aLista4 := aMatriz[ 4 ]
nPos := ASCan( aLista3, { | e | ! Empty( e ) } )
? aLista1[ nPos ]
É o mesmo anterior, apenas dei nome a cada lista.
É o que o seu FOR/NEXT sugere sobre o que está querendo fazer.
Neste aqui chamei de lista1,2,3,4, mas no anterior usei direto aMatriz[ 1 ] e aMatriz[ 3 ]
criar expressão para Ascan
Enviado: 06 Mai 2021 12:39
por JoséQuintas
Precisa confirmar sobre o array.
Poderia ser:
Código: Selecionar todos
{ { codigo, codigo, codigo }, { nome, nome, nome }, { valor, valor, valor } )
ou
Código: Selecionar todos
{ { codigo, nome, valor }, { codigo, nome, valor }, { codigo, nome, valor } )
Pra achar qual tem valor zero, depende de como ele está distribuído, se da primeira forma ou da segunda.
criar expressão para Ascan
Enviado: 06 Mai 2021 12:54
por JoséQuintas
No primeiro caso, que cada campo está numa lista, é pesquisar na LISTA DE VALORES, e pegar o nome da LISTA DE NOMES
Código: Selecionar todos
nPos := AScan( array[ 3 ], { | e | e != 0 } ) // pesquisa a coluna 3=lista de valores
cNome := array[ 2 ][ nPos ] // pega da coluna 2=lista de nomes
No segundo caso, é olhar cada um da LISTA, e pegar o CAMPO NOME dessa lista
Código: Selecionar todos
nPos := ASCan( array, { | e | e[ 3 ] != 0 } ) // pesquisa na lista geral em cada elemento, a coluna 3=valor
cNome := array[ nPos ] [ 2 ] // pega da lista geral coluna 2=nome
Chamando de lista, e do que tem em cada lista, parece ficar mais claro
Nota: array[ nPos, 2 ] e array[ nPos ][ 2 ] são equivalentes, pode escrever dos dois jeitos.
Mas array[ nPos, 2 ] é diferente de array[ 2, nPos ], são posições diferentes.
criar expressão para Ascan
Enviado: 07 Mai 2021 09:40
por juniorcamilo
Código: Selecionar todos
if AScan( aMatEntrada[27],{ | e | ! Empty( e ) }) # 0
........
endif
funcionou perfeitamente!
obrigado pela excelente aula!