#c# #stopwatch
#c# #секундомер
Вопрос:
Кто-нибудь знает, как я могу добавить функцию таймера в этот код, который решает головоломки судоку? Я пробовал класс Stopwatch, но не могу заставить его работать, потому что я точно не знаю, куда его поместить. Я пробовал несколько мест, но всегда получаю ошибки. Основная цель кода работает, но я хотел бы добавить функцию таймера, чтобы увидеть, как долго выполнялся код.
using System;
namespace SuDoKu
{
public class SuDoKu
{
private int[,] grid;
public SuDoKu()
{
grid = new int[9, 9];
}
static void Main(string[] args)
{
SuDoKu sdk = new SuDoKu();
int[,] grd = {
{ 0, 0, 0, 0, 0, 0, 0, 0, 0 },
{ 0, 0, 0, 0, 0, 0, 0, 0, 0 },
{ 0, 0, 0, 0, 0, 0, 0, 0, 0 },
{ 0, 0, 0, 0, 0, 0, 0, 0, 0 },
{ 0, 0, 0, 0, 0, 0, 0, 0, 0 },
{ 0, 0, 0, 0, 0, 0, 0, 0, 0 },
{ 0, 0, 0, 0, 0, 0, 0, 0, 0 },
{ 0, 0, 0, 0, 0, 0, 0, 0, 0 },
{ 0, 0, 0, 0, 0, 0, 0, 0, 0 } };
for(int i = 0; i < 9; i )
for(int j = 0; j < 9; j )
sdk.EnterToGrid(grd[i, j], new Point(i, j));
Console.WriteLine("Original Grid");
sdk.Display();
sdk.Solve(sdk.NextAvailableCell(), new Point());
Console.WriteLine("nnnSolved Grid");
sdk.Display();
Console.WriteLine();
}
public void Display()
{
for(int i = 0; i < 9; i )
{
Console.WriteLine();
for(int j = 0; j < 9; j )
{
if(ShowFromGrid(new Point(i, j)) == 0) {
Console.Write("0 ");
}
else
{
Console.Write(ShowFromGrid(new Point(i, j)) " ");
}
if(j == 2 || j == 5)
{
Console.Write("| ");
}
}
if(i == 2 || i == 5) {
Console.Write("n------|-------|------ ");
}
}
}
public void EnterToGrid(int num, Point pos) {
grid[pos.X, pos.Y] = num;
}
public int ShowFromGrid(Point pos) {
return grid[pos.X, pos.Y];
}
public void Solve(Point pos, Point prevPos) {
if(pos.X < 9 amp;amp; pos.Y < 9)
{
Point posPrev = new Point();
if(grid[pos.X, pos.Y] == 0)
{
for(int i = 1; i <= 9; i )
{
if(IsThisNumberPossibleInTheGrid(i, pos))
{
grid[pos.X, pos.Y] = i;
posPrev.X = pos.X;
posPrev.Y = pos.Y;
Point posNext = NextAvailableCell();
if(!posNext.Equals(new Point()))
Solve(posNext, posPrev);
}
}
if(grid[pos.X, pos.Y] == 0)
{
if(!prevPos.Equals(new Point()))
grid[prevPos.X, prevPos.Y] = 0;
return;
}
}
}
else
{
Point posNext = NextAvailableCell();
if(!posNext.Equals(new Point()))
Solve(posNext, pos);
}
}
public Point NextAvailableCell()
{
for(int i = 0; i < 9; i )
for(int j = 0; j < 9; j )
if(grid[i, j] == 0)
return new Point(i, j);
return new Point();
}
public bool IsThisNumberPossibleInTheGrid(int num, Point pos) {
if(IsThisNumberPossibleInTheBlock(num, pos))
{
for(int i = 0; i < 9; i )
{
if(grid[i, pos.Y] == num amp;amp; pos.X != i)
{
return false;
}
if(grid[pos.X, i] == num amp;amp; pos.Y != i)
{
return false;
}
}
return true;
}
return false;
}
public bool IsThisNumberPossibleInTheBlock(int num, Point pos)
{
Point Grid = new Point();
Grid.X = (pos.X >= 0 amp;amp; pos.X <= 2) ? 0 : ((pos.X >= 3 amp;amp; pos.X <= 5) ? 3 : ((pos.X >= 6 amp;amp; pos.X <= 8) ? 6 : -1));
Grid.Y = (pos.Y >= 0 amp;amp; pos.Y <= 2) ? 0 : ((pos.Y >= 3 amp;amp; pos.Y <= 5) ? 3 : ((pos.Y >= 6 amp;amp; pos.Y <= 8) ? 6 : -1));
if(!Grid.Equals(new Point()))
{
for(int i = Grid.X; i < Grid.X 3; i )
{
for(int j = Grid.Y; j < Grid.Y 3; j )
{
if(grid[i, j] == num amp;amp; !pos.Equals(new Point(i, j)))
return false;
}
}
return true;
}
return false;
}
}
public class Point
{
public int X;
public int Y;
public Point()
{
this.X = -1;
this.Y = -1;
}
public Point(int x, int y)
{
this.X = x;
this.Y = y;
}
public bool Equals(Point p)
{
return (this.X == p.X amp;amp; this.Y == p.Y) ? true : false;
}
}
}
Ответ №1:
Объект Stopwatch часто используется для (как вы делаете здесь) измерения того, сколько времени занимает выполнение задания. Здесь следует помнить одну быструю вещь: на все, что вы делаете, уйдет время между запуском и остановкой, поэтому убедитесь, что вы помещаете только тот фактический код, который хотите использовать между ними.
using System.Diagnostics;
//...
void StopwatchUsingMethod()
{
//A: Setup and stuff you don't want timed
var timer = new Stopwatch();
timer.Start();
//B: Run stuff you want timed
timer.Stop();
TimeSpan timeTaken = timer.Elapsed;
string foo = "Time taken: " timeTaken.ToString(@"m:ss.fff");
}
Foo здесь покажет минуты, секунды и миллисекунды, которые потребовались для завершения, хотя будет отображаться как неправильный, если это займет более 59 минут. Более подробную информацию о сроках можно найти здесь: https://docs.microsoft.com/en-us/dotnet/standard/base-types/custom-timespan-format-strings
Если я правильно понимаю ваш код, вы хотите поместить все до первой sdk.Display();
строки включительно в раздел A и поместить вызов для решения только в раздел B. Так что что-то вроде
static void Main(string[] args)
{
//...
sdk.Display();
var timer = new Stopwatch();
timer.Start();
sdk.Solve(sdk.NextAvailableCell(), new Point());
timer.Stop();
Console.WriteLine("nnnSolved Grid");
//...you can use the time taken here
}
Комментарии:
1. Спасибо, это было очень полезно.
Ответ №2:
«Основная цель кода работает, но я хотел бы добавить функцию таймера, чтобы увидеть, как долго выполнялся код»
Для этого вы можете использовать System.Diagnostics.Stopwatch
(https://docs.microsoft.com/en-us/dotnet/api/system.diagnostics.stopwatch?view=netframework-4.7.2 ). Если вы хотите узнать, сколько времени требуется для выполнения функции, добавьте stopWatch.Start()
до и stopWatch.Stop()
после вызовов функции. Теперь вы можете увидеть общее время, которое потребовалось (в секундах / миллисекундах и т.д.), Используя stopWatch.Elapsed
, в зависимости от вашего удобства.