dbSkip() travando programa após 47 cliques

Discussão sobre a biblioteca Fivewin - O Clipper para Windows.

Moderador: Moderadores

maiconlst
Usuário Nível 1
Usuário Nível 1
Mensagens: 13
Registrado em: 15 Jul 2014 16:36
Localização: Paracatu/MG

dbSkip() travando programa após 47 cliques

Mensagem por maiconlst »

Olá.

Tenho encontrado o seguinte problema:

Para atualizar uma listbox movendo o ponteiro pela tabela de um banco de dados ".dbf" utilizo um botão para avançar e outro para retroceder com a função DbSkip().
A função faz seu trabalho normalmente, no entanto ao clicar 47 vezes o programa deixa de funcionar.

Poderia ser alguma coisa relacionada a uso de memória ou algo assim?
alxsts
Colaborador
Colaborador
Mensagens: 3107
Registrado em: 12 Ago 2008 15:50
Localização: São Paulo-SP-Brasil

dbSkip() travando programa após 47 cliques

Mensagem por alxsts »

Olá!

Olhando o enunciado do problema, lembrei daquela música "Mistérios da meia noite...."

Parece algum loop infinito, estouro de pilha, etc...

Que tal postar o código para análise?
[]´s
Alexandre Santos (AlxSts)
Avatar do usuário
Itamar M. Lins Jr.
Administrador
Administrador
Mensagens: 8028
Registrado em: 30 Mai 2007 11:31
Localização: Ilheus Bahia
Curtiu: 2 vezes
Curtiram: 1 vez

dbSkip() travando programa após 47 cliques

Mensagem por Itamar M. Lins Jr. »

Clica só 46 vezes!

Sem ver o código fica difícil responder algo.

Saudações,
Itamar M. Lins Jr.
Saudações,
Itamar M. Lins Jr.
Avatar do usuário
JoséQuintas
Administrador
Administrador
Mensagens: 20415
Registrado em: 26 Fev 2007 11:59
Localização: São Paulo-SP
Curtiram: 1 vez

dbSkip() travando programa após 47 cliques

Mensagem por JoséQuintas »

Lembro de detalhes assim no VB6.....
Em ambiente GUI tudo funciona isoladamente, mesmo junto.
Ao clicar, ele começa o processamento e se clicar de novo, vai processar de novo.
Até aí parece normal, mas significa que a rotina pode estar rodando duas vezes ao mesmo tempo.
Por isso convém ao clicar, a primeira coisa seria desativar o(s) botão(ões), e só liberar depois de terminar o processo.

E a listbox... poderão ser várias rotinas mexendo nessa listbox ao mesmo tempo, e aí entra aquele negócio de usar Mutex pra controlar o acesso a variável por várias rotinas ao mesmo tempo, algo parecido com RLock(), só que ao invés de fazer isso com registro de arquivo, vai fazer com a variável de memória.

Programar em GUI requer cuidados extras, porque é multithread, tá tudo rodando ao mesmo tempo.

Mas pensando em algo simples.... colocou a checagem de Eof() ?
José M. C. Quintas
Harbour 3.2, mingw, multithread, gtwvg, fivewin 25.12, dbfcdx, MySQL, ADOClass, PDFClass, SefazClass, (hwgui), (hmg3), (hmg extended), (oohg), PNotepad, ASP, (Linux/Flagship/harbour 3.2)
"The world is full of kings and queens, who blind our eyes and steal our dreams Its Heaven and Hell"

https://github.com/JoseQuintas/
Euclides
Usuário Nível 3
Usuário Nível 3
Mensagens: 154
Registrado em: 12 Mai 2007 14:07
Localização: São Paulo, Capital

dbSkip() travando programa após 47 cliques

Mensagem por Euclides »

Nosso amiguinho maiconlst já colocou este post no forum da Fivewin.br, portanto o LISTBOX não é do Harbour.
Pode ser o WBROWSE, XBROWSE ou mesmo o TCBROWSE... como vai saber...
Como os colegas já colocaram, é difícil dizer qualquer coisa sem ver as fontes.
Na pasta SAMPLES do Fivewin, existem vários exemplos de Listbox. Cansei de fazer SKIP(+1) e SKIP(-1) n´eles.
Vamos esperar o maiconlst se manifestar.
T+
Euclides
maiconlst
Usuário Nível 1
Usuário Nível 1
Mensagens: 13
Registrado em: 15 Jul 2014 16:36
Localização: Paracatu/MG

dbSkip() travando programa após 47 cliques

Mensagem por maiconlst »

Aqui vai o trecho em questão. Se trata de um depurador que tem uma listbox com os nomes dos alias e ao clicar em um registro, abre-se outra listbox com os dados em questão que serão passados para frente ou para tras para se saber o que acontece na tabela com o objetivo de no caso de estar acontecendo um loop no momento da depuração ou algo assim e se saber o que "se passa" na tabela.

Código: Selecionar todos

If vNexPre=="P"  /*variavel que diferencia qual botao pressionado para avançar ou retroceder */                               
   &vNameAlias.->(DbSkip())                                                   
   If (&vNameAlias.->(RecNo()))==vLastRecNo   /*"variavel que confere se o ultimo recno antes de apertar o botao"*/                                                                   
      MsgInfo("Este é o último registro da tabela, não é mais possível avançar.")
      vLimTab:="U" /* "variavel usada no "When" do redefine do botão para deixar o botão ativo ou inativo"*/
ElseIf vNexPre=="A"     
   &vNameAlias.->(DbSkip(-1)) 
   If (&vNameAlias.->(RecNo()))==vLastRecNo
      MsgInfo("Este é o primeiro registro da tabela, não é mais possível avançar.")
      vLimTab:="P" 
   EndIf        			   
EndIf 
maiconlst
Usuário Nível 1
Usuário Nível 1
Mensagens: 13
Registrado em: 15 Jul 2014 16:36
Localização: Paracatu/MG

dbSkip() travando programa após 47 cliques

Mensagem por maiconlst »

Abaixo a ListBox:

Código: Selecionar todos

     @ 2.0,1 ListBox ListDebug; 
      Fields cValToChar(VetorDebug[ListDebug:nAt,01]),;
		       cValToChar(VetorDebug[ListDebug:nAt,02]),;
		       cValToChar(VetorDebug[ListDebug:nAt,03]),;
		       cValToChar(VetorDebug[ListDebug:nAt,04]),;
		       cValToChar(VetorDebug[ListDebug:nAt,05]),;
		       cValToChar(VetorDebug[ListDebug:nAt,06]); 				  	                     
      Headers "Campo",;
      	      "Tipo",;
              "Tamanho",;
              "Decimal",;
	      "Flags",;
	      "Valor"; 
      FieldSizes 75,35,35,40,35,150;  
		Size 269,100; 
      Of DialogDebug
maiconlst
Usuário Nível 1
Usuário Nível 1
Mensagens: 13
Registrado em: 15 Jul 2014 16:36
Localização: Paracatu/MG

dbSkip() travando programa após 47 cliques

Mensagem por maiconlst »

A questão do EOF() e do BOF() foi me falado tambem no forum do fivewin. Mas mesmo assim o problema persiste.

No caso eu uso um refresh na listbox e finalizo a Dialog a cada clique fazendo assim com que haja a atualização. Para passar os parametros chamo mesma função novamente. Poderia isso estar causando um acumulo de memoria ou algo assim?
Euclides
Usuário Nível 3
Usuário Nível 3
Mensagens: 154
Registrado em: 12 Mai 2007 14:07
Localização: São Paulo, Capital

dbSkip() travando programa após 47 cliques

Mensagem por Euclides »

Bom dia,
Com as informações acima, continua difícil fazer qualquer análise. Mas dá para sugerir algo:
1 - Não há necessidade de fechar o DIALOG e reabri-lo. Utilizando oLbx:Refresh() e oDlg:Update() resolve.
Acho que só isso deveria aumentar bem o número de dbskip´s permitidos.
2 - Em vez de usar dbskip(), poderia utilizar oLbx:GoUp() e oLbx:GoDown(). Isso eliminaria o tratamento to EOF()/BOF().
Tente isso e informe.
T+, Euclides
maiconlst
Usuário Nível 1
Usuário Nível 1
Mensagens: 13
Registrado em: 15 Jul 2014 16:36
Localização: Paracatu/MG

dbSkip() travando programa após 47 cliques

Mensagem por maiconlst »

Prezados. Consegui resolver o problema. Coloquei os 'dbskip' e as estruturas que moviam o ponteiro em uma função separada acabando com o problema que era na verdade a recursividade.

Obrigado a Todos. :xau
alxsts
Colaborador
Colaborador
Mensagens: 3107
Registrado em: 12 Ago 2008 15:50
Localização: São Paulo-SP-Brasil

dbSkip() travando programa após 47 cliques

Mensagem por alxsts »

Olá!
alxsts escreveu:Parece algum loop infinito, estouro de pilha, etc...
[]´s
Alexandre Santos (AlxSts)
maiconlst
Usuário Nível 1
Usuário Nível 1
Mensagens: 13
Registrado em: 15 Jul 2014 16:36
Localização: Paracatu/MG

dbSkip() travando programa após 47 cliques

Mensagem por maiconlst »

Creio que o problema era a questão de estouro de pilha mesmo. Porque a função que fazia essa questão do Dbskip chamava ela mesma. A recursividade gerava o Overflow.
Responder