Nota
O acesso a esta página requer autorização. Pode tentar iniciar sessão ou alterar os diretórios.
O acesso a esta página requer autorização. Pode tentar alterar os diretórios.
Na parte 2 desta série de tutoriais, você mergulha um pouco mais fundo nos recursos de compilação e depuração do Visual Studio necessários para o desenvolvimento diário. Esses recursos incluem gerenciamento de vários projetos, depuração e referência a pacotes de terceiros. Execute o aplicativo de console C# criado na Parte 1 deste tutoriale explore alguns recursos do ambiente de desenvolvimento integrado (IDE) do Visual Studio. Este tutorial é a parte 2 de uma série de tutoriais em duas partes.
Neste tutorial, você conclui as seguintes tarefas:
- Adicione um segundo projeto.
- Referenciar bibliotecas e adicionar pacotes.
- Depure seu código.
- Inspecione o código concluído.
Pré-requisitos
Para trabalhar neste artigo, você pode usar qualquer um destes aplicativos de calculadora:
- A aplicação de consola da calculadora da parte 1 deste tutorial.
- O aplicativo de calculadora C# no repositório vs-tutorial-samples. Para começar, abrir o aplicativo no repositório.
Adicionar outro projeto
O código do mundo real envolve projetos trabalhando juntos em uma solução. Você pode adicionar um projeto de biblioteca de classes ao seu aplicativo de calculadora que fornece algumas funções de calculadora.
No Visual Studio, você usa o comando de menu Arquivo>Adicionar>Novo Projeto para adicionar um novo projeto. Você também pode clicar com o botão direito do mouse na solução em Gerenciador de Soluções para adicionar um projeto no menu de contexto.
No Gerenciador de Soluções , clique com o botão direito do mouse no nó da solução e escolha Adicionar>Novo Projeto.
Na janela Adicionar um novo projeto, digite biblioteca de classes na caixa de pesquisa. Escolha o modelo de projeto biblioteca de classes C# e, em seguida, selecione Avançar.
No ecrã Configurar o novo projeto, digite o nome do projeto CalculatorLibrarye selecione Avançar.
Escolha .NET 3.1 quando solicitado. O Visual Studio cria o novo projeto e o adiciona à solução.
Renomeie o arquivo Class1.cs para CalculatorLibrary.cs. Para renomear o arquivo, você pode clicar com o botão direito do mouse no nome em Gerenciador de Soluções e escolher Renomear, selecione o nome e pressione F2ou selecione o nome e selecione novamente para digitar.
Uma mensagem pode perguntar se você deseja renomear referências para
Class1no arquivo. Não importa como você responde, porque você substituirá o código em uma etapa futura.Agora, adicione uma referência de projeto, para que o primeiro projeto possa usar APIs que a nova biblioteca de classes expõe. Clique com o botão direito do mouse no nó Dependências do na Calculadora de projeto e escolha Adicionarde referência do projeto .
A caixa de diálogo Reference Manager é exibida. Nesta caixa de diálogo, você pode adicionar referências a outros projetos, assemblies e DLLs COM que seus projetos precisam.
Na caixa de diálogo Reference Manager, marque a caixa de seleção para o projeto CalculatorLibrary e, em seguida, selecione OK.
A referência do projeto aparece sob um nó Projetos no Gerenciador de Soluções .
No Program.cs, selecione a classe
Calculatore todo o seu código e pressione Ctrl+X para cortá-la. Em seguida, no CalculatorLibrary.cs, cole o código no namespaceCalculatorLibrary.Adicione também
publicantes da classe Calculator para expô-la fora da biblioteca.CalculatorLibrary.cs agora deve se assemelhar ao seguinte código:
// CalculatorLibrary.cs using System; namespace CalculatorLibrary { public class Calculator { public static double DoOperation(double num1, double num2, string op) { double result = double.NaN; // Default value is "not-a-number" if an operation, such as division, could result in an error. // Use a switch statement to do the math. switch (op) { case "a": result = num1 + num2; break; case "s": result = num1 - num2; break; case "m": result = num1 * num2; break; case "d": // Ask the user to enter a non-zero divisor. if (num2 != 0) { result = num1 / num2; } break; // Return text for an incorrect option entry. default: break; } return result; } } }Program.cs também tem uma referência, mas um erro diz que a chamada
Calculator.DoOperationnão é resolvida. O erro é porqueCalculatorLibraryestá em um namespace diferente. Para obter uma referência totalmente qualificada, você pode adicionar o namespaceCalculatorLibraryà chamadaCalculator.DoOperationem Program.cs:// Program.cs result = CalculatorLibrary.Calculator.DoOperation(cleanNum1, cleanNum2, op);Ou, você pode tentar adicionar uma diretiva
usingao início do arquivo Program.cs:// Program.cs using CalculatorLibrary;Adicionar a diretiva
usingdeve permitir remover o namespaceCalculatorLibrarydo site de chamada, mas agora há uma ambiguidade. ÉCalculatora classe emCalculatorLibraryou éCalculatoro namespace?Para resolver a ambiguidade, renomeie o namespace de
CalculatorparaCalculatorProgramem Program.cs.// Program.cs namespace CalculatorProgram
No Gerenciador de Soluções , clique com o botão direito do mouse no nó da solução e escolha Adicionar>Novo Projeto.
Na janela Adicionar um novo projeto, digite biblioteca de classes na caixa de pesquisa. Escolha o modelo de projeto biblioteca de classes C# e, em seguida, selecione Avançar.
No ecrã Configurar o novo projeto, digite o nome do projeto CalculatorLibrarye selecione Avançar.
No ecrã de Informações adicionais, .NET 8.0 está selecionado. Selecione Criar.
O Visual Studio cria o novo projeto e o adiciona à solução.
Renomeie o arquivo Class1.cs para CalculatorLibrary.cs. Para renomear o arquivo, você pode clicar com o botão direito do mouse no nome em Gerenciador de Soluções e escolher Renomear, selecione o nome e pressione F2ou selecione o nome e selecione novamente para digitar.
Uma mensagem pode perguntar se você deseja renomear todas as referências para
Class1no arquivo. Não importa como você responde, porque você substituirá o código em uma etapa futura.Agora, adicione uma referência de projeto, para que o primeiro projeto possa usar APIs que a nova biblioteca de classes expõe. Clique com o botão direito do mouse no nó Dependências do na Calculadora de projeto e escolha Adicionarde referência do projeto .
A caixa de diálogo Reference Manager é exibida. Nesta caixa de diálogo, você pode adicionar referências a outros projetos, assemblies e DLLs COM que seus projetos precisam.
Na caixa de diálogo Reference Manager, marque a caixa de seleção para o projeto CalculatorLibrary e, em seguida, selecione OK.
A referência do projeto aparece sob um nó Projetos no Gerenciador de Soluções .
No Program.cs, selecione a classe
Calculatore todo o seu código e pressione Ctrl+X para cortá-la. Em seguida, no CalculatorLibrary.cs, cole o código no namespaceCalculatorLibrary.Adicione também
publicantes da classe Calculator para expô-la fora da biblioteca.CalculatorLibrary.cs agora deve se assemelhar ao seguinte código:
// CalculatorLibrary.cs namespace CalculatorLibrary { public class Calculator { public static double DoOperation(double num1, double num2, string op) { double result = double.NaN; // Default value is "not-a-number" if an operation, such as division, could result in an error. // Use a switch statement to do the math. switch (op) { case "a": result = num1 + num2; break; case "s": result = num1 - num2; break; case "m": result = num1 * num2; break; case "d": // Ask the user to enter a non-zero divisor. if (num2 != 0) { result = num1 / num2; } break; // Return text for an incorrect option entry. default: break; } return result; } } }Program.cs também tem uma referência, mas um erro diz que a chamada
Calculator.DoOperationnão é resolvida. O erro é porqueCalculatorLibraryestá em um namespace diferente. Para obter uma referência totalmente qualificada, você pode adicionar o namespaceCalculatorLibraryà chamadaCalculator.DoOperationem Program.cs:// Program.cs result = CalculatorLibrary.Calculator.DoOperation(cleanNum1, cleanNum2, op);Ou, você pode tentar adicionar uma diretiva
usingao início do arquivo Program.cs:// Program.cs using CalculatorLibrary;Adicionar a diretiva
usingdeve permitir remover o namespaceCalculatorLibrarydo site de chamada.Se o código
Program.csestiver no namespaceCalculator, renomeie o namespace deCalculatorparaCalculatorProgrampara remover a ambiguidade entre o nome da classe e o nome do namespace.
Bibliotecas .NET de referência: Gravar em um registo
Você pode usar a classe .NET Trace para adicionar um log de todas as operações e gravá-lo em um arquivo de texto. A classe Trace também é útil para técnicas básicas de depuração de impressão. A classe Trace está em System.Diagnosticse utiliza classes System.IO como StreamWriter.
Comece por adicionar as
usingdiretivas no topo de CalculatorLibrary.cs:// CalculatorLibrary.cs using System.IO; using System.Diagnostics;Esse uso da classe
Tracedeve manter uma referência para a classe, que ela associa a um fluxo de arquivos. Esse requisito significa que a calculadora funciona melhor como um objeto, portanto, adicione um construtor no início da classeCalculatorem CalculatorLibrary.cs.Remova também a palavra-chave
staticpara alterar o métodoDoOperationestático em um método membro.// CalculatorLibrary.cs public Calculator() { StreamWriter logFile = File.CreateText("calculator.log"); Trace.Listeners.Add(new TextWriterTraceListener(logFile)); Trace.AutoFlush = true; Trace.WriteLine("Starting Calculator Log"); Trace.WriteLine(String.Format("Started {0}", System.DateTime.Now.ToString())); } public double DoOperation(double num1, double num2, string op) {Adicione a saída de log a cada cálculo.
DoOperationdeverá agora parecer-se com o seguinte código:// CalculatorLibrary.cs public double DoOperation(double num1, double num2, string op) { double result = double.NaN; // Default value is "not-a-number" if an operation, such as division, could result in an error. // Use a switch statement to do the math. switch (op) { case "a": result = num1 + num2; Trace.WriteLine(String.Format("{0} + {1} = {2}", num1, num2, result)); break; case "s": result = num1 - num2; Trace.WriteLine(String.Format("{0} - {1} = {2}", num1, num2, result)); break; case "m": result = num1 * num2; Trace.WriteLine(String.Format("{0} * {1} = {2}", num1, num2, result)); break; case "d": // Ask the user to enter a non-zero divisor. if (num2 != 0) { result = num1 / num2; Trace.WriteLine(String.Format("{0} / {1} = {2}", num1, num2, result)); } break; // Return text for an incorrect option entry. default: break; } return result; }Em Program.cs, uma linha vermelha ondulada agora marca a chamada estática. Para corrigir o erro, crie uma variável
calculatoradicionando a seguinte linha de código imediatamente antes do loopwhile (!endApp):// Program.cs Calculator calculator = new Calculator();Modifique também o site de chamada
DoOperationpara fazer referência ao objeto chamadocalculatorem minúsculas. O código agora é uma chamada de membro, em vez de uma chamada para um método estático.// Program.cs result = calculator.DoOperation(cleanNum1, cleanNum2, op);Execute o aplicativo novamente. Quando terminar, clique com o botão direito no nó do projeto Calculadora de e escolha Abrir Pasta no Explorador do Windows.
No Explorador de Ficheiros, navegue para a pasta de saída em bin/Debug/net8.0 (ou qualquer versão do .NET que estiver a usar) e abra o ficheiro calculator.log. A saída deve ser algo como isto:
Starting Calculator Log Started 7/9/2020 1:58:19 PM 1 + 2 = 3 3 * 3 = 9
Neste ponto, CalculatorLibrary.cs deve se assemelhar a este código:
// CalculatorLibrary.cs
using System;
using System.IO;
using System.Diagnostics;
namespace CalculatorLibrary
{
public class Calculator
{
public Calculator()
{
StreamWriter logFile = File.CreateText("calculator.log");
Trace.Listeners.Add(new TextWriterTraceListener(logFile));
Trace.AutoFlush = true;
Trace.WriteLine("Starting Calculator Log");
Trace.WriteLine(String.Format("Started {0}", System.DateTime.Now.ToString()));
}
public double DoOperation(double num1, double num2, string op)
{
double result = double.NaN; // Default value is "not-a-number" if an operation, such as division, could result in an error.
// Use a switch statement to do the math.
switch (op)
{
case "a":
result = num1 + num2;
Trace.WriteLine(String.Format("{0} + {1} = {2}", num1, num2, result));
break;
case "s":
result = num1 - num2;
Trace.WriteLine(String.Format("{0} - {1} = {2}", num1, num2, result));
break;
case "m":
result = num1 * num2;
Trace.WriteLine(String.Format("{0} * {1} = {2}", num1, num2, result));
break;
case "d":
// Ask the user to enter a non-zero divisor.
if (num2 != 0)
{
result = num1 / num2;
Trace.WriteLine(String.Format("{0} / {1} = {2}", num1, num2, result));
}
break;
// Return text for an incorrect option entry.
default:
break;
}
return result;
}
}
}
Program.cs deve ser semelhante ao seguinte código:
// Program.cs
using System;
using CalculatorLibrary;
namespace CalculatorProgram
{
class Program
{
static void Main(string[] args)
{
bool endApp = false;
// Display title as the C# console calculator app.
Console.WriteLine("Console Calculator in C#\r");
Console.WriteLine("------------------------\n");
Calculator calculator = new Calculator();
while (!endApp)
{
// Declare variables and set to empty.
string numInput1 = "";
string numInput2 = "";
double result = 0;
// Ask the user to type the first number.
Console.Write("Type a number, and then press Enter: ");
numInput1 = Console.ReadLine();
double cleanNum1 = 0;
while (!double.TryParse(numInput1, out cleanNum1))
{
Console.Write("This is not valid input. Please enter an integer value: ");
numInput1 = Console.ReadLine();
}
// Ask the user to type the second number.
Console.Write("Type another number, and then press Enter: ");
numInput2 = Console.ReadLine();
double cleanNum2 = 0;
while (!double.TryParse(numInput2, out cleanNum2))
{
Console.Write("This is not valid input. Please enter an integer value: ");
numInput2 = Console.ReadLine();
}
// Ask the user to choose an operator.
Console.WriteLine("Choose an operator from the following list:");
Console.WriteLine("\ta - Add");
Console.WriteLine("\ts - Subtract");
Console.WriteLine("\tm - Multiply");
Console.WriteLine("\td - Divide");
Console.Write("Your option? ");
string op = Console.ReadLine();
try
{
result = calculator.DoOperation(cleanNum1, cleanNum2, op);
if (double.IsNaN(result))
{
Console.WriteLine("This operation will result in a mathematical error.\n");
}
else Console.WriteLine("Your result: {0:0.##}\n", result);
}
catch (Exception e)
{
Console.WriteLine("Oh no! An exception occurred trying to do the math.\n - Details: " + e.Message);
}
Console.WriteLine("------------------------\n");
// Wait for the user to respond before closing.
Console.Write("Press 'n' and Enter to close the app, or press any other key and Enter to continue: ");
if (Console.ReadLine() == "n") endApp = true;
Console.WriteLine("\n"); // Friendly linespacing.
}
return;
}
}
}
Você pode usar a classe .NET Trace para adicionar um log de todas as operações e gravá-lo em um arquivo de texto. A classe Trace também é útil para técnicas básicas de depuração de impressão. A classe Trace está em System.Diagnosticse utiliza classes System.IO como StreamWriter.
Comece por adicionar as
usingdiretivas no topo de CalculatorLibrary.cs:// CalculatorLibrary.cs using System.Diagnostics;Esse uso da classe
Tracedeve manter uma referência para a classe, que ela associa a um fluxo de arquivos. Esse requisito significa que a calculadora funciona melhor como um objeto, portanto, adicione um construtor no início da classeCalculatorem CalculatorLibrary.cs.Remova também a palavra-chave
staticpara alterar o métodoDoOperationestático em um método membro.// CalculatorLibrary.cs public Calculator() { StreamWriter logFile = File.CreateText("calculator.log"); Trace.Listeners.Add(new TextWriterTraceListener(logFile)); Trace.AutoFlush = true; Trace.WriteLine("Starting Calculator Log"); Trace.WriteLine(String.Format("Started {0}", System.DateTime.Now.ToString())); } public double DoOperation(double num1, double num2, string op) {Adicione a saída de log a cada cálculo.
DoOperationdeverá agora parecer-se com o seguinte código:// CalculatorLibrary.cs public double DoOperation(double num1, double num2, string op) { double result = double.NaN; // Default value is "not-a-number" if an operation, such as division, could result in an error. // Use a switch statement to do the math. switch (op) { case "a": result = num1 + num2; Trace.WriteLine(String.Format("{0} + {1} = {2}", num1, num2, result)); break; case "s": result = num1 - num2; Trace.WriteLine(String.Format("{0} - {1} = {2}", num1, num2, result)); break; case "m": result = num1 * num2; Trace.WriteLine(String.Format("{0} * {1} = {2}", num1, num2, result)); break; case "d": // Ask the user to enter a non-zero divisor. if (num2 != 0) { result = num1 / num2; Trace.WriteLine(String.Format("{0} / {1} = {2}", num1, num2, result)); } break; // Return text for an incorrect option entry. default: break; } return result; }Em Program.cs, uma linha vermelha ondulada agora marca a chamada estática. Para corrigir o erro, crie uma variável
calculatoradicionando a seguinte linha de código imediatamente antes do loopwhile (!endApp):// Program.cs Calculator calculator = new Calculator();Modifique também o site de chamada
DoOperationpara fazer referência ao objeto chamadocalculatorem minúsculas. O código agora é uma chamada de membro, em vez de uma chamada para um método estático.// Program.cs result = calculator.DoOperation(cleanNum1, cleanNum2, op);Execute o aplicativo novamente. Quando terminar, clique com o botão direito no nó do projeto Calculadora de e escolha Abrir Pasta no Explorador do Windows.
No Explorador de Ficheiros, navegue até à pasta de saída em bin/Debug/e abra o ficheiro calculator.log. A saída deve ser algo como isto:
Starting Calculator Log Started 7/9/2020 1:58:19 PM 1 + 2 = 3 3 * 3 = 9
Neste ponto, CalculatorLibrary.cs deve se assemelhar a este código:
// CalculatorLibrary.cs
using System.Diagnostics;
namespace CalculatorLibrary
{
public class Calculator
{
public Calculator()
{
StreamWriter logFile = File.CreateText("calculator.log");
Trace.Listeners.Add(new TextWriterTraceListener(logFile));
Trace.AutoFlush = true;
Trace.WriteLine("Starting Calculator Log");
Trace.WriteLine(String.Format("Started {0}", System.DateTime.Now.ToString()));
}
public double DoOperation(double num1, double num2, string op)
{
double result = double.NaN; // Default value is "not-a-number" if an operation, such as division, could result in an error.
// Use a switch statement to do the math.
switch (op)
{
case "a":
result = num1 + num2;
Trace.WriteLine(String.Format("{0} + {1} = {2}", num1, num2, result));
break;
case "s":
result = num1 - num2;
Trace.WriteLine(String.Format("{0} - {1} = {2}", num1, num2, result));
break;
case "m":
result = num1 * num2;
Trace.WriteLine(String.Format("{0} * {1} = {2}", num1, num2, result));
break;
case "d":
// Ask the user to enter a non-zero divisor.
if (num2 != 0)
{
result = num1 / num2;
Trace.WriteLine(String.Format("{0} / {1} = {2}", num1, num2, result));
}
break;
// Return text for an incorrect option entry.
default:
break;
}
return result;
}
}
}
Program.cs deve ser semelhante ao seguinte código:
// Program.cs
using CalculatorLibrary;
namespace CalculatorProgram
{
class Program
{
static void Main(string[] args)
{
bool endApp = false;
// Display title as the C# console calculator app.
Console.WriteLine("Console Calculator in C#\r");
Console.WriteLine("------------------------\n");
Calculator calculator = new Calculator();
while (!endApp)
{
// Declare variables and set to empty.
// Use Nullable types (with ?) to match type of System.Console.ReadLine
string? numInput1 = "";
string? numInput2 = "";
double result = 0;
// Ask the user to type the first number.
Console.Write("Type a number, and then press Enter: ");
numInput1 = Console.ReadLine();
double cleanNum1 = 0;
while (!double.TryParse(numInput1, out cleanNum1))
{
Console.Write("This is not valid input. Please enter an integer value: ");
numInput1 = Console.ReadLine();
}
// Ask the user to type the second number.
Console.Write("Type another number, and then press Enter: ");
numInput2 = Console.ReadLine();
double cleanNum2 = 0;
while (!double.TryParse(numInput2, out cleanNum2))
{
Console.Write("This is not valid input. Please enter an integer value: ");
numInput2 = Console.ReadLine();
}
// Ask the user to choose an operator.
Console.WriteLine("Choose an operator from the following list:");
Console.WriteLine("\ta - Add");
Console.WriteLine("\ts - Subtract");
Console.WriteLine("\tm - Multiply");
Console.WriteLine("\td - Divide");
Console.Write("Your option? ");
string? op = Console.ReadLine();
// Validate input is not null, and matches the pattern
if (op == null || ! Regex.IsMatch(op, "[a|s|m|d]"))
{
Console.WriteLine("Error: Unrecognized input.");
}
else
{
try
{
result = calculator.DoOperation(cleanNum1, cleanNum2, op);
if (double.IsNaN(result))
{
Console.WriteLine("This operation will result in a mathematical error.\n");
}
else Console.WriteLine("Your result: {0:0.##}\n", result);
}
catch (Exception e)
{
Console.WriteLine("Oh no! An exception occurred trying to do the math.\n - Details: " + e.Message);
}
}
Console.WriteLine("------------------------\n");
// Wait for the user to respond before closing.
Console.Write("Press 'n' and Enter to close the app, or press any other key and Enter to continue: ");
if (Console.ReadLine() == "n") endApp = true;
Console.WriteLine("\n"); // Friendly linespacing.
}
return;
}
}
}
Adicionar um pacote NuGet: gravar em um arquivo JSON
Para operações de saída em JSON, um formato popular e portátil para armazenar dados de objetos, você pode fazer referência ao pacote Newtonsoft.Json NuGet. Os pacotes NuGet são o principal método de distribuição para bibliotecas de classes .NET.
No Explorador de Soluções , clique com o botão direito do mouse no nó Dependências do projeto CalculatorLibrary e escolha Gerir Pacotes NuGet.
O Gerenciador de Pacotes NuGet é aberto.
Procure e selecione o pacote Newtonsoft.Json e selecione Instalar.
O Visual Studio baixa o pacote e o adiciona ao projeto. Uma nova entrada aparece no nó Referências no Gerenciador de Soluções .
Se você for solicitado a aceitar alterações, selecione OK.
O Visual Studio baixa o pacote e o adiciona ao projeto. Uma nova entrada aparece no nó Pacotes no Gerenciador de Soluções .
Adicionar uma diretiva
usingparaNewtonsoft.Jsonno início de CalculatorLibrary.cs.// CalculatorLibrary.cs using Newtonsoft.Json;Crie o
JsonWriterobjeto de membro e substitua o construtorCalculatorcom o seguinte código:// CalculatorLibrary.cs JsonWriter writer; public Calculator() { StreamWriter logFile = File.CreateText("calculatorlog.json"); logFile.AutoFlush = true; writer = new JsonTextWriter(logFile); writer.Formatting = Formatting.Indented; writer.WriteStartObject(); writer.WritePropertyName("Operations"); writer.WriteStartArray(); }Modifique o método
DoOperationpara adicionar o código JSONwriter:// CalculatorLibrary.cs public double DoOperation(double num1, double num2, string op) { double result = double.NaN; // Default value is "not-a-number" if an operation, such as division, could result in an error. writer.WriteStartObject(); writer.WritePropertyName("Operand1"); writer.WriteValue(num1); writer.WritePropertyName("Operand2"); writer.WriteValue(num2); writer.WritePropertyName("Operation"); // Use a switch statement to do the math. switch (op) { case "a": result = num1 + num2; writer.WriteValue("Add"); break; case "s": result = num1 - num2; writer.WriteValue("Subtract"); break; case "m": result = num1 * num2; writer.WriteValue("Multiply"); break; case "d": // Ask the user to enter a non-zero divisor. if (num2 != 0) { result = num1 / num2; } writer.WriteValue("Divide"); break; // Return text for an incorrect option entry. default: break; } writer.WritePropertyName("Result"); writer.WriteValue(result); writer.WriteEndObject(); return result; }Adicione um método para concluir a sintaxe JSON assim que o usuário terminar de inserir os dados da operação.
// CalculatorLibrary.cs public void Finish() { writer.WriteEndArray(); writer.WriteEndObject(); writer.Close(); }No final de Program.cs, antes do
return;, adicione uma chamada paraFinish:// Program.cs // Add call to close the JSON writer before return calculator.Finish(); return; }Crie e execute o aplicativo e, depois de inserir algumas operações, feche o aplicativo digitando o comando n.
Abra o ficheiro calculatorlog.json no Explorador de Ficheiros. Você deve ver algo como o seguinte conteúdo:
{ "Operations": [ { "Operand1": 2.0, "Operand2": 3.0, "Operation": "Add", "Result": 5.0 }, { "Operand1": 3.0, "Operand2": 4.0, "Operation": "Multiply", "Result": 12.0 } ] }
Depurar: definir e atingir um ponto de interrupção
O depurador do Visual Studio é uma ferramenta poderosa. O depurador pode percorrer seu código para encontrar o ponto exato onde há um erro de programação. Em seguida, você pode entender quais correções precisa fazer e fazer alterações temporárias para continuar executando seu aplicativo.
No Program.cs, clique com o botão do rato na margem à esquerda da seguinte linha de código. Você também pode clicar na linha e selecionar F9ou clicar com o botão direito do mouse na linha e selecionar Ponto de interrupção>Inserir ponto de interrupção.
// Program.cs result = calculator.DoOperation(cleanNum1, cleanNum2, op);O ponto vermelho que aparece indica um ponto de interrupção. Você pode usar pontos de interrupção para pausar seu aplicativo e inspecionar o código. Você pode definir um ponto de interrupção em qualquer linha executável de código.
Crie e execute o aplicativo. Insira os seguintes valores para o cálculo:
- Para o primeiro número, digite 8.
- Para o segundo número, digite 0.
- Quanto ao operador, vamos divertir-nos. Digite d.
O aplicativo suspende onde você criou o ponto de interrupção, que é indicado pelo ponteiro amarelo à esquerda e pelo código realçado. O código destacado ainda não foi executado.
Agora, com o aplicativo suspenso, você pode inspecionar o estado do aplicativo.
Depurar: Exibir variáveis
No código realçado, passe o mouse sobre variáveis como
cleanNum1eop. Os valores atuais para essas variáveis,8edrespectivamente, aparecem em DataTips.
Ao depurar, verificar se as variáveis mantêm os valores esperados geralmente é fundamental para corrigir problemas.
No painel inferior, observe a janela Locais. Se estiver fechado, selecione Depurar>Windows>Locais para abri-lo.
A janela Locals mostra cada variável que está atualmente no escopo, juntamente com o seu valor e tipo.
Olhe para a Autos janela.
A janela Autos é semelhante à janela Locals, mas mostra as variáveis imediatamente anteriores e posteriores à linha de código atual em que seu aplicativo está pausado.
Observação
Se não vir a janela Automáticos, selecione Depurar>Windows>Autos para abri-la.
Em seguida, execute o código no depurador uma instrução de cada vez, processo chamado de execução passo a passo.
Depuração: Passo a passo pelo código
Pressione F11ou selecione Depurar>Entrar em.
Usando o comando Step Into, o aplicativo executa a instrução atual e avança para a próxima instrução executável, geralmente a próxima linha de código. O ponteiro amarelo à esquerda sempre indica a declaração atual.
Você acabou de entrar no método
DoOperationna classeCalculator.Para obter uma visão hierárquica do fluxo do seu programa, consulte a janela Call Stack . Se estiver fechado, selecione Depurar>>Windows Pilha de Chamadas para abri-lo.
Esta vista mostra o método
Calculator.DoOperationatual, indicado pelo ponteiro amarelo. A segunda linha mostra a função que chamou o método, a partir do métodoMainem Program.cs.A janela Call Stack mostra a ordem em que os métodos e funções estão sendo chamados. Esta janela também fornece acesso a muitos recursos do depurador, como Go to Source Code, a partir de seu menu de atalho.
Pressione F10ou selecione Depurar>Step Over, várias vezes até que o aplicativo pause na instrução
switch.// CalculatorLibrary.cs switch (op) {O comando Step Over é semelhante ao comando Step In, exceto que, se a instrução atual chamar uma função, o depurador executará o código na função e não suspenderá a execução até que a função retorne. Step Over é mais rápido do que Step Into se você não estiver interessado em uma função específica.
Pressione F10 mais uma vez, para que o aplicativo pause na seguinte linha de código.
// CalculatorLibrary.cs if (num2 != 0) {Este código verifica se há um caso de divisão por zero. Se o aplicativo continuar, ele lançará uma exceção geral (um erro), mas você pode querer tentar outra coisa, como visualizar o valor real retornado no console. Uma opção é usar um recurso de depurador chamado editar e continuar para alterar o código e depois continuar a depuração. No entanto, há um truque diferente para modificar temporariamente o fluxo de execução.
Depurar: Testar uma alteração temporária
Selecione o ponteiro amarelo, atualmente pausado na instrução
if (num2 != 0), e arraste-o para a seguinte instrução:// CalculatorLibrary.cs result = num1 / num2;Arrastar o ponteiro aqui faz com que o aplicativo ignore completamente a instrução
if, para que você possa ver o que acontece quando você divide por zero.Pressione F10 para executar a linha de código.
Se você passar o mouse sobre a variável
result, ela mostrará um valor de Infinito. Em C#, Infinito é o resultado quando você divide por zero.Pressione F5ou selecione Depurar>Continuar a Depuração.
O símbolo do infinito aparece no console como resultado da operação matemática.
Feche o aplicativo corretamente digitando o comando n.
Código completo
Aqui está o código completo para o arquivo CalculatorLibrary.cs, depois de concluir todas as etapas:
// CalculatorLibrary.cs
using System;
using System.IO;
using Newtonsoft.Json;
namespace CalculatorLibrary
{
public class Calculator
{
JsonWriter writer;
public Calculator()
{
StreamWriter logFile = File.CreateText("calculatorlog.json");
logFile.AutoFlush = true;
writer = new JsonTextWriter(logFile);
writer.Formatting = Formatting.Indented;
writer.WriteStartObject();
writer.WritePropertyName("Operations");
writer.WriteStartArray();
}
public double DoOperation(double num1, double num2, string op)
{
double result = double.NaN; // Default value is "not-a-number" if an operation, such as division, could result in an error.
writer.WriteStartObject();
writer.WritePropertyName("Operand1");
writer.WriteValue(num1);
writer.WritePropertyName("Operand2");
writer.WriteValue(num2);
writer.WritePropertyName("Operation");
// Use a switch statement to do the math.
switch (op)
{
case "a":
result = num1 + num2;
writer.WriteValue("Add");
break;
case "s":
result = num1 - num2;
writer.WriteValue("Subtract");
break;
case "m":
result = num1 * num2;
writer.WriteValue("Multiply");
break;
case "d":
// Ask the user to enter a non-zero divisor.
if (num2 != 0)
{
result = num1 / num2;
}
writer.WriteValue("Divide");
break;
// Return text for an incorrect option entry.
default:
break;
}
writer.WritePropertyName("Result");
writer.WriteValue(result);
writer.WriteEndObject();
return result;
}
public void Finish()
{
writer.WriteEndArray();
writer.WriteEndObject();
writer.Close();
}
}
}
E aqui está o código para Program.cs:
// Program.cs
using System;
using CalculatorLibrary;
namespace CalculatorProgram
{
class Program
{
static void Main(string[] args)
{
bool endApp = false;
// Display title as the C# console calculator app.
Console.WriteLine("Console Calculator in C#\r");
Console.WriteLine("------------------------\n");
Calculator calculator = new Calculator();
while (!endApp)
{
// Declare variables and set to empty.
string numInput1 = "";
string numInput2 = "";
double result = 0;
// Ask the user to type the first number.
Console.Write("Type a number, and then press Enter: ");
numInput1 = Console.ReadLine();
double cleanNum1 = 0;
while (!double.TryParse(numInput1, out cleanNum1))
{
Console.Write("This is not valid input. Please enter an integer value: ");
numInput1 = Console.ReadLine();
}
// Ask the user to type the second number.
Console.Write("Type another number, and then press Enter: ");
numInput2 = Console.ReadLine();
double cleanNum2 = 0;
while (!double.TryParse(numInput2, out cleanNum2))
{
Console.Write("This is not valid input. Please enter an integer value: ");
numInput2 = Console.ReadLine();
}
// Ask the user to choose an operator.
Console.WriteLine("Choose an operator from the following list:");
Console.WriteLine("\ta - Add");
Console.WriteLine("\ts - Subtract");
Console.WriteLine("\tm - Multiply");
Console.WriteLine("\td - Divide");
Console.Write("Your option? ");
string op = Console.ReadLine();
try
{
result = calculator.DoOperation(cleanNum1, cleanNum2, op);
if (double.IsNaN(result))
{
Console.WriteLine("This operation will result in a mathematical error.\n");
}
else Console.WriteLine("Your result: {0:0.##}\n", result);
}
catch (Exception e)
{
Console.WriteLine("Oh no! An exception occurred trying to do the math.\n - Details: " + e.Message);
}
Console.WriteLine("------------------------\n");
// Wait for the user to respond before closing.
Console.Write("Press 'n' and Enter to close the app, or press any other key and Enter to continue: ");
if (Console.ReadLine() == "n") endApp = true;
Console.WriteLine("\n"); // Friendly linespacing.
}
calculator.Finish();
return;
}
}
}
Aqui está o código completo para o arquivo CalculatorLibrary.cs, depois de concluir todas as etapas:
// CalculatorLibrary.cs
using Newtonsoft.Json;
namespace CalculatorLibrary
{
public class Calculator
{
JsonWriter writer;
public Calculator()
{
StreamWriter logFile = File.CreateText("calculatorlog.json");
logFile.AutoFlush = true;
writer = new JsonTextWriter(logFile);
writer.Formatting = Formatting.Indented;
writer.WriteStartObject();
writer.WritePropertyName("Operations");
writer.WriteStartArray();
}
public double DoOperation(double num1, double num2, string op)
{
double result = double.NaN; // Default value is "not-a-number" if an operation, such as division, could result in an error.
writer.WriteStartObject();
writer.WritePropertyName("Operand1");
writer.WriteValue(num1);
writer.WritePropertyName("Operand2");
writer.WriteValue(num2);
writer.WritePropertyName("Operation");
// Use a switch statement to do the math.
switch (op)
{
case "a":
result = num1 + num2;
writer.WriteValue("Add");
break;
case "s":
result = num1 - num2;
writer.WriteValue("Subtract");
break;
case "m":
result = num1 * num2;
writer.WriteValue("Multiply");
break;
case "d":
// Ask the user to enter a non-zero divisor.
if (num2 != 0)
{
result = num1 / num2;
}
writer.WriteValue("Divide");
break;
// Return text for an incorrect option entry.
default:
break;
}
writer.WritePropertyName("Result");
writer.WriteValue(result);
writer.WriteEndObject();
return result;
}
public void Finish()
{
writer.WriteEndArray();
writer.WriteEndObject();
writer.Close();
}
}
}
E aqui está o código para Program.cs:
// Program.cs
using CalculatorLibrary;
namespace CalculatorProgram
{
class Program
{
static void Main(string[] args)
{
bool endApp = false;
// Display title as the C# console calculator app.
Console.WriteLine("Console Calculator in C#\r");
Console.WriteLine("------------------------\n");
Calculator calculator = new Calculator();
while (!endApp)
{
// Declare variables and set to empty.
// Use Nullable types (with ?) to match type of System.Console.ReadLine
string? numInput1 = "";
string? numInput2 = "";
double result = 0;
// Ask the user to type the first number.
Console.Write("Type a number, and then press Enter: ");
numInput1 = Console.ReadLine();
double cleanNum1 = 0;
while (!double.TryParse(numInput1, out cleanNum1))
{
Console.Write("This is not valid input. Please enter an integer value: ");
numInput1 = Console.ReadLine();
}
// Ask the user to type the second number.
Console.Write("Type another number, and then press Enter: ");
numInput2 = Console.ReadLine();
double cleanNum2 = 0;
while (!double.TryParse(numInput2, out cleanNum2))
{
Console.Write("This is not valid input. Please enter an integer value: ");
numInput2 = Console.ReadLine();
}
// Ask the user to choose an operator.
Console.WriteLine("Choose an operator from the following list:");
Console.WriteLine("\ta - Add");
Console.WriteLine("\ts - Subtract");
Console.WriteLine("\tm - Multiply");
Console.WriteLine("\td - Divide");
Console.Write("Your option? ");
string? op = Console.ReadLine();
// Validate input is not null, and matches the pattern
if (op == null || ! Regex.IsMatch(op, "[a|s|m|d]"))
{
Console.WriteLine("Error: Unrecognized input.");
}
else
{
try
{
result = calculator.DoOperation(cleanNum1, cleanNum2, op);
if (double.IsNaN(result))
{
Console.WriteLine("This operation will result in a mathematical error.\n");
}
else Console.WriteLine("Your result: {0:0.##}\n", result);
}
catch (Exception e)
{
Console.WriteLine("Oh no! An exception occurred trying to do the math.\n - Details: " + e.Message);
}
}
Console.WriteLine("------------------------\n");
// Wait for the user to respond before closing.
Console.Write("Press 'n' and Enter to close the app, or press any other key and Enter to continue: ");
if (Console.ReadLine() == "n") endApp = true;
Console.WriteLine("\n"); // Friendly linespacing.
}
calculator.Finish();
return;
}
}
}
Próximos passos
Parabéns por concluir este tutorial! Para saber mais, continue com o seguinte conteúdo:
- Continue com mais tutoriais em C#
- Guia de início rápido: criar um aplicativo Web ASP.NET Core
- Aprenda a depurar código C# no Visual Studio
- Passo a passo sobre como criar e executar testes de unidade
- Executar um programa em C#
- Saiba mais sobre o C# IntelliSense
- Continue com a visão geral do IDE do Visual Studio
- Registo e rastreio