[AJUDA] Como continuar a contagem de um TimeOut enquanto o programa aguarda a ação do usuário?

1. [AJUDA] Como continuar a contagem de um TimeOut enquanto o programa aguarda a ação do usuário?

Maurilio Cardoso Gonçalves
macgonca

(usa Fedora)

Enviado em 13/08/2021 - 22:00h

Olá colegas!

Sou estudante de Python e preciso de um apoio técnico para completar uma condição específica de funcionamento do programa que desenvolvi. O resumo do laboratório e o programa podem ser verificados no GitHub neste link: https://github.com/ChesterNut999/Python_Lab_06_Test_Py_Posto_Combustivel#mp";

O desafio consiste em: No módulo 3 do programa (checkout) é necessário a inclusão de um TimeOut em relação a sessão do usuário:

Condição 1 - um contador de 30 segundos deve ser iniciado ao chegar na etapa de checkout.
Condição 2 - se o usuário não realizar nenhuma ação durante os 30 segundos, TimeOut com saída do código (exit(0)).
Condição 3 - o contador só deve parar quando o usuário tomar alguma decisão e avançar para a próxima etapa do programa.

A dificuldade é que o contador FOR fica "travado" quando o input entra e a contagem para.
Alguém consegue me ajudar?

Att,
ChesterNut999


  


2. Re: [AJUDA] Como continuar a contagem de um TimeOut enquanto o programa aguarda a ação do usuário?

Samuel Leonardo
SamL

(usa XUbuntu)

Enviado em 14/08/2021 - 01:47h

Isso que você quer é impossível sem usar outra thread. Já vi outras perguntas parecidas, inclusive, tive essa mesma dúvida no passado em outra linguagem.
É comum ter essa dúvida quando se estuda sockets.
Com um thread a parte, ela pode simplesmente tentar encerrar o programa, apesar de que não sei se isso é permitido.
Seria algo assim:
1-mostra a mengaem dos 30 segundos
2-inicia a excução da thread por 30 segundos
3-na thread, se passar de 30 segundos, mostra mensagem de encerramento
4-por fim, chama um jeito de encerrar o processo pai através da thread.


3. Re: [AJUDA] Como continuar a contagem de um TimeOut enquanto o programa aguarda a ação do usuário?

Maurilio Cardoso Gonçalves
macgonca

(usa Fedora)

Enviado em 17/08/2021 - 12:19h


SamL escreveu:

Isso que você quer é impossível sem usar outra thread. Já vi outras perguntas parecidas, inclusive, tive essa mesma dúvida no passado em outra linguagem.
É comum ter essa dúvida quando se estuda sockets.
Com um thread a parte, ela pode simplesmente tentar encerrar o programa, apesar de que não sei se isso é permitido.
Seria algo assim:
1-mostra a mengaem dos 30 segundos
2-inicia a excução da thread por 30 segundos
3-na thread, se passar de 30 segundos, mostra mensagem de encerramento
4-por fim, chama um jeito de encerrar o processo pai através da thread.


Estou preso nesse código. Ele funciona mas o problema agora é na saída, ou seja, o contador sobrescreve o input.
Consegue ver uma possível solução?

import threading
import time, sys
from threading import Thread

def contador():
for count in reversed(range(11)):
time.sleep(0.5)
sys.stdout.flush()
sys.stdout.write("\rESTA SESSÃO SERÁ ENCERRADA AUTOMATICAMENTE EM " + str(count) + " SEGUNDOS")

if count == 0:
print("\nTEMPO LIMITE ATINGIDO! SESSÃO ENCERRADA AUTOMATICAMENTE!")
exit(0)

else:
continue

def msg():
time.sleep(1)
sys.stdout.flush()
opcao = int(input("\nDigite 1 para encerrar o loop: "))

if opcao == 1:
print("FIM")
exit(0)

def tasks():
thread_1 = Thread(target=contador)
thread_2 = Thread(target=msg)
thread_1.start()
thread_2.start()

if __name__ == '__main__':
tasks()







4. Re: [AJUDA] Como continuar a contagem de um TimeOut enquanto o programa aguarda a ação do usuário?

Samuel Leonardo
SamL

(usa XUbuntu)

Enviado em 17/08/2021 - 15:32h

É, isso esqueci de falar. Como a saida padrão (stdout) é apenas um, toda vez que qualquer thread imprimir algo, sairá sobrescrevendo o stdout.
O que eu sugiro e o seguinte:
-ao invés de imprimir a mensagem de alerta para cada segundo passado, você pode imprimir ela apenas uma vez.
Por exemplo:
Coloque para imprimir apenas uma vez a "sys.stdout.write("\rESTA SESSÃO SERÁ ENC...", ou seja, só imprime esta mensagem quando o count for 11 e for 0
Nesse caso, vc imprime apenas duas vezes.
Você não precisa imprimir todo tempo a mensagem, a não ser é claro, que você manipule o terminal para evitar sobrecarregar o stdout.
Por exemplo, se vc usar o "\r" no final da string de saída, ele vai imprimir na mesma linha sempre, mas ai você precisa mudar mais um pouco seu código.
É um jeito de fazer mas talvez vc não queira assim.

Não se preocupe se seu programa não funciona de maneira perfeitamente como imaginou.
Quando a gente faz software pra usuários leigos, eles querem coisas realmente impossíveis de fazer com qualquer linguagem.
Uma vez foi me pedido fazer um programa com duas entradas para serem digitadas, daí o programa devia pegar dois números de 18 digitos cada.
E ainda pediram pra criar outro número concatenando esses dois, ou seja, daria um número de 36 digitos. Disseram que tinha que ser um número e eu disse ser impossível porque 36 digitos seria acima do valor de um inteiro comum, daí tive que explicar a coisa toda até a pessoa entender que era impossível. No final, acabei transformando o número em string rsrsrs


5. Re: [AJUDA] Como continuar a contagem de um TimeOut enquanto o programa aguarda a ação do usuário?

Maurilio Cardoso Gonçalves
macgonca

(usa Fedora)

Enviado em 17/08/2021 - 21:25h


SamL escreveu:

É, isso esqueci de falar. Como a saida padrão (stdout) é apenas um, toda vez que qualquer thread imprimir algo, sairá sobrescrevendo o stdout.
O que eu sugiro e o seguinte:
-ao invés de imprimir a mensagem de alerta para cada segundo passado, você pode imprimir ela apenas uma vez.
Por exemplo:
Coloque para imprimir apenas uma vez a "sys.stdout.write("\rESTA SESSÃO SERÁ ENC...", ou seja, só imprime esta mensagem quando o count for 11 e for 0
Nesse caso, vc imprime apenas duas vezes.
Você não precisa imprimir todo tempo a mensagem, a não ser é claro, que você manipule o terminal para evitar sobrecarregar o stdout.
Por exemplo, se vc usar o "\r" no final da string de saída, ele vai imprimir na mesma linha sempre, mas ai você precisa mudar mais um pouco seu código.
É um jeito de fazer mas talvez vc não queira assim.

Não se preocupe se seu programa não funciona de maneira perfeitamente como imaginou.
Quando a gente faz software pra usuários leigos, eles querem coisas realmente impossíveis de fazer com qualquer linguagem.
Uma vez foi me pedido fazer um programa com duas entradas para serem digitadas, daí o programa devia pegar dois números de 18 digitos cada.
E ainda pediram pra criar outro número concatenando esses dois, ou seja, daria um número de 36 digitos. Disseram que tinha que ser um número e eu disse ser impossível porque 36 digitos seria acima do valor de um inteiro comum, daí tive que explicar a coisa toda até a pessoa entender que era impossível. No final, acabei transformando o número em string rsrsrs


Bom colega, eu sei que é possível de alguma forma. Acho que minha lógica não está correta...
Consegui um resultado bem próximo do que quero. Só preciso estudar uma forma de manter o contador na mesma linha e faze-lo parar. Pela biblioteca Thread foi possível colocar os dois processos em paralelo. Veja o código abaixo:

import time, sys
from threading import Thread

def contador():
for count in reversed(range(11)):
time.sleep(1)
sys.stdout.flush()
print(end='\r' + "ESTA SESSÃO SERÁ ENCERRADA AUTOMATICAMENTE EM " + str(count) + " SEGUNDOS")

if count > 0:
process_2 = Thread(target=msg)
process_2.start()
continue

elif count == 0:
print("\nTEMPO LIMITE ATINGIDO! SESSÃO ENCERRADA AUTOMATICAMENTE!")
break

elif msg == 1:
break

def msg():
opcao = int(input("\nDigite 1 para encerrar o loop: "))

if opcao == 1:
print("\nFIM")
return int(opcao)

else:
while opcao != 1:
continue

if __name__ == '__main__':
thread_1 = Thread(target=contador)
thread_1.start()




6. Re: [AJUDA] Como continuar a contagem de um TimeOut enquanto o programa aguarda a ação do usuário?

Samuel Leonardo
SamL

(usa XUbuntu)

Enviado em 17/08/2021 - 22:12h

Bom colega, eu sei que é possível de alguma forma. Acho que minha lógica não está correta...

Eu tentei ajudar no que eu sei fazer. Creio que pra fazer exatamente como vc quer na sua mente teria de usar alguma lib externa que manipulasse o terminal, tipo a ncurses. Ai nem precisria de Thread pra fazer "malabarismos" rsrsrs
Boa sorte ai.






Patrocínio

Site hospedado pelo provedor RedeHost.
Linux banner

Destaques

Artigos

Dicas

Tópicos

Top 10 do mês

Scripts