Aritmética de Tempo
Parte da seção Lógica & Fluxo do Journey de GO da Coddy — lição 63 de 68.
Agora que você entende os objetos time.Time e os valores time.Duration, você pode realizar operações aritméticas para calcular horários passados ou futuros. Go fornece dois métodos essenciais para aritmética de tempo: Add e Sub.
O método Add recebe um time.Duration e retorna um novo time.Time que representa o horário original mais a duração:
now := time.Now()
tomorrow := now.Add(24 * time.Hour)
fmt.Println(tomorrow)O método Sub funciona de duas maneiras. Quando você subtrai um time.Time de outro, ele retorna um time.Duration representando a diferença entre eles:
start := time.Now()
end := start.Add(2 * time.Hour)
difference := end.Sub(start) // Retorna 2h0m0sEsses métodos tornam simples o cálculo de prazos, a medição do tempo decorrido ou o agendamento de eventos futuros. O objeto time.Time original permanece inalterado - ambos os métodos retornam novos valores, seguindo a preferência do Go por operações imutáveis.
Esta lição inclui um quiz rápido. Comece a lição para respondê-lo e acompanhar seu progresso.
Esta lição inclui um quiz rápido. Comece a lição para respondê-lo e acompanhar seu progresso.
Esta lição inclui um quiz rápido. Comece a lição para respondê-lo e acompanhar seu progresso.
Desafio
FácilCrie uma calculadora de prazos de projeto que utilize aritmética de tempo para determinar marcos e prazos do projeto. Este desafio testará sua habilidade de usar os métodos Add e Sub em objetos time.Time para calcular datas futuras e diferenças de tempo entre eventos.
Você receberá duas entradas:
- Uma string contendo informações de início do projeto no formato
"year:month:day:hour:minute"(ex:"2024:1:15:9:0") - Uma string contendo durações de tarefas no formato
"task1:duration_value:duration_unit,task2:duration_value:duration_unit"(ex:"Planning:5:Day,Development:3:Week,Testing:10:Day")
Sua tarefa é:
- Analisar a primeira entrada dividindo-a por dois pontos para extrair os valores de ano, mês, dia, hora e minuto
- Converter esses valores de string para inteiros e criar um horário de início do projeto usando
time.Date(usetime.UTCpara a localização, 0 para segundos e nanossegundos) - Analisar a segunda entrada dividindo-a por vírgulas para obter as entradas de tarefas individuais
- Para cada entrada de tarefa, dividir por dois pontos para extrair o nome da tarefa, o valor da duração e a unidade de duração
- Converter os valores de duração para inteiros e criar objetos
time.Durationusando as constantes apropriadas:- Para
"Day": multiplique por24 * time.Hour - Para
"Week": multiplique por7 * 24 * time.Hour - Para
"Hour": multiplique portime.Hour
- Para
- Exibir o cabeçalho da aplicação:
"=== PROJECT DEADLINE CALCULATOR ===" - Exibir o início do projeto:
"Project start time: [start_time_object]" - Calcular os prazos das tarefas adicionando a duração de cada tarefa ao horário de término da tarefa anterior (a primeira tarefa começa no horário de início do projeto):
- Para cada tarefa, exibir:
"Task: [task_name]"" Duration: [duration_object]"" Start: [task_start_time]"" End: [task_end_time]"(calculado usando o métodoAdd)
- Calcular e exibir a linha do tempo do projeto:
"=== PROJECT TIMELINE ===""Project start: [start_time_object]""Project end: [final_task_end_time]""Total project duration: [total_duration_object]"(calculado usando o métodoSubentre o fim e o início do projeto)
- Exibir a análise das tarefas:
"=== TASK ANALYSIS ===""Number of tasks: [number_of_tasks]""Longest task: [longest_task_name] ([longest_duration_object])""Shortest task: [shortest_task_name] ([shortest_duration_object])"
- Calcular o tempo entre tarefas consecutivas e exibir os intervalos:
"=== TASK TRANSITIONS ==="- Para cada par de tarefas consecutivas:
"[first_task_name] to [second_task_name]: [time_difference_object]"(deve ser 0, pois as tarefas são consecutivas)
- Exibir as estatísticas do projeto:
"=== PROJECT STATISTICS ===""Total working days: [total_duration_in_hours_divided_by_24]""Total working hours: [total_duration_in_hours]""Project spans [number_of_calendar_days] calendar days"
- Exibir a mensagem de conclusão:
"Project timeline calculation completed successfully"
Use o pacote time para operações de tempo, o pacote strings para dividir as strings de entrada, o pacote strconv para converter strings em inteiros e o pacote fmt para saída formatada. Lembre-se que o método Add retorna um novo objeto time.Time representando o tempo original mais a duração, e o método Sub retorna um time.Duration representando a diferença entre dois tempos. Este desafio demonstra como construir um cronograma de projeto completo usando operações aritméticas de tempo.
Folha de consulta
Go fornece dois métodos essenciais para aritmética de tempo: Add e Sub.
O método Add recebe um time.Duration e retorna um novo time.Time:
now := time.Now()
tomorrow := now.Add(24 * time.Hour)O método Sub subtrai um time.Time de outro e retorna um time.Duration:
start := time.Now()
end := start.Add(2 * time.Hour)
difference := end.Sub(start) // Retorna 2h0m0sAmbos os métodos retornam novos valores sem modificar o objeto time.Time original.
Experimente você mesmo
package main
import (
"fmt"
"strconv"
"strings"
"time"
)
func main() {
// Ler a entrada
var startInfo string
var taskInfo string
fmt.Scanln(&startInfo)
fmt.Scanln(&taskInfo)
// Analisar as informações do horário de início
startParts := strings.Split(startInfo, ":")
year, _ := strconv.Atoi(startParts[0])
month, _ := strconv.Atoi(startParts[1])
day, _ := strconv.Atoi(startParts[2])
hour, _ := strconv.Atoi(startParts[3])
minute, _ := strconv.Atoi(startParts[4])
// Criar o horário de início do projeto
startTime := time.Date(year, time.Month(month), day, hour, minute, 0, 0, time.UTC)
// Analisar as informações das tarefas
taskEntries := strings.Split(taskInfo, ",")
// TODO: Escreva seu código abaixo
// - Processar cada entrada de tarefa para extrair nome, valor de duração e unidade
// - Criar objetos de duração para cada tarefa
// - Calcular os horários de início e término das tarefas
// - Encontrar as tarefas mais longas e mais curtas
// - Calcular as estatísticas do projeto
// - Exibir todas as seções de saída obrigatórias
// A saída será gerada pela sua implementação acima
}Esta lição inclui um quiz rápido. Comece a lição para respondê-lo e acompanhar seu progresso.
Todas as lições de Lógica & Fluxo
1Fluxo de Controle Avançado
Switch com `fallthrough`Interrompendo Loops AninhadosContinuando um Loop EspecíficoA Instrução `goto`Recapitulação - Controle de Loop Avançado4Projeto: Lista de Tarefas Simples
Configuração do ProjetoAdicionando uma Tarefa7Tratamento de Erros em Profundidade
Tipos de Erro PersonalizadosWrapping de Erros com `%w`Unwrapping com `errors.Is`Unwrapping com `errors.As`Entendendo o `panic`Usando o `recover`Recapitulação - Divisão Segura10Trabalhando com Tempo
Obtendo o Horário AtualCriando um Horário EspecíficoFormatando o TempoParsing de Strings de TempoDuração de TempoAritmética de TempoSleep e TickersRecapitulação - Timer Simples2Structs e Métodos
Definindo Métodos em StructsRecebedores de ValorRecebedores de PonteiroEscolhendo RecebedoresMétodos vs FunçõesRecapitulação - Comportamento de Structs5Mapas em Profundidade
Mapas de StructsPonteiros como Valores de MapVerificando Mapas NilComparando MapasRecapitulação - Contador de Frequência de Palavras3Interfaces (O Básico)
O que é uma Interface?Definindo uma InterfaceImplementando uma InterfaceUsando Tipos de InterfaceInterface VaziaAsserções de TipoType SwitchRecapitulação - Formas e Comportamentos