Input examples:
7 9 12 16 18 21 25 27 30 34 36 39 43 45 48 52 54 57 61
7 9 12 16 18 21 25 27 30 34 36 39 43 45 48 52 54 57 ... 75 79
Note that it ends with a space.
I want to get 57 in the first case and 75 in the second case as integer. I tried with the following:
Convert.ToInt32(Shorten(sequence).Split(' ').ElementAt(sequence.Length - 2));
The problem is that sequence.Length is not really the right index.
You can use the overload for Split() and pass the RemoveEmptyEntires enum:
string input = "7 9 12 16 18 21 25 27 30 34 36 39 43 45 48 52 54 57 61 ";
var splitInput = input.Split(new char[0], StringSplitOptions.RemoveEmptyEntries);
var inputInt = Convert.ToInt32(splitInput[splitInput.Length - 2]);
// inputInt is 57
Doing it this way allows your last element to actually be what you want.
Fiddle here
Based on maccettura's answer, in C# 8 you can simplify index acces like so
var input = "1 2 3";
var parts = input.Split(' ', StringSplitOptions.RemoveEmptyEntries);
var value = parts.Length >= 2 ? Convert.ToInt32(parts[^2]) : null;
How about something that doesn't use strings at all.
public static int? SplitReverseInt(this string str, int ixFromBack)
{
var inWord = false;
var wEnd = 0;
var found = 0;
for (int i = str.Length - 1; i >= 0; i--)
{
var charr = str[i];
if (char.IsWhiteSpace(charr))
{
// we found the beginning of a word
if (inWord)
{
if (found == ixFromBack)
{
var myInt = 0;
for (int j = i+1; j <= wEnd; j++)
myInt = (myInt * 10 + str[j] - '0');
return myInt;
}
inWord = false;
found++;
}
}
else
{
if (!inWord)
{
wEnd = i;
inWord = true;
}
}
}
// word (number) is at the beginning of the string
if (inWord && found == ixFromBack)
{
var myInt = 0;
for (int j = 0; j <= wEnd; j++)
myInt = (myInt * 10 + str[j] - '0');
return myInt;
}
return null;
}
Performance is about 10 times faster on the example strings.
This only loops from the back, and only fetches one number, it doesnt create substrings or an array of strings we don't need.
Use like this:
var numberFromBack = SplitReverseInt(input, 1);
I've been trying to develop an algorithm to show which tiles you can move to on a square board based on these parameters:
-You move your characters around the board each turn to any tile within their movement speed.
-Each horizontal/vertical movement is worth 1 tile.
-Each diagonal is worth 1.5 (rounded down- so the first diagonal is worth 1, and the second is worth 2, and back to 1, etc.).
-You cannot move a character onto a tile that has another character on it, so you must go around.
NOTE: I don't currently check to see if a tile is occupied, I want to take this one step at a time, and the first step is getting a correct result of which tiles the character can go to.
I have a 3d array the size of the board. The third dimension has two layers, the first one is initialized as all 99 except the character you are moving (the origin), which is set to 0. This dimension contains the distance to the origin from each tile.
The other layer contains the number of diagonals it took to get to that tile.
Basically I have a recursive function that checks each adjacent tile for the lowest distance to the origin, and sets the current tile to that lowest distance number +1 (or +2 if it is the second diagonal). It moves out from the origin recursively, using the tiles it already filled in to generate a map of all of the potential tiles that it can move to.
`
const int edgeOfBoard = 15;
static int[,,] movementCount = new int[edgeOfBoard, edgeOfBoard, 2]; //movement speed/diagonals tracking matrix
static void Main()
{
int movementSpeed = 4; //number of tiles character can move
int x = 7; //x starting position
int y = 7; //y starting position
for(int i = 0; i < edgeOfBoard; i++) //fill movementCount with 99
{
for(int j = 0; j < edgeOfBoard; j++)
{
movementCount[i, j, 0] = 99;
}
}
movementCount[x, y, 0] = 0; //set origin (character's location) as 0 movements from itself
pathfinder(movementSpeed, x, y, 0); //run pathfinder algorithm
print(); //print result
}
private static void print() //print result
{
for(int y = 0; y < edgeOfBoard; y++) //print movement to get to a given tile
{
for(int x = 0; x < edgeOfBoard; x++)
{
if(movementCount[x, y, 0] == 99) //replace 99s with " " to make it easier to read
{
Console.Write("| ");
}else
{
Console.Write("|" + movementCount[x, y, 0]);
}
}
Console.WriteLine("|");
}
Console.WriteLine();
for(int y = 0; y < edgeOfBoard; y++) //print diagonals needed to get to a given tile
{
for(int x = 0; x < edgeOfBoard; x++)
{
if(movementCount[x, y, 1] == 0)
{
Console.Write("| ");
}else
{
Console.Write("|" + movementCount[x, y, 1]);
}
}
Console.WriteLine("|");
}
}
internal static void pathfinder(int movementSpeed, int x, int y, int depth)
{
if (depth <= movementSpeed) //cuts off when limit is reached
{
for (int Y = -1; Y <= 1; Y++) //checks all adjacent tiles
{
for (int X = -1; X <= 1; X++)
{
//Console.WriteLine("y = " + y + ", Y = " + Y + ", x = " + x + ", X = " + X + ", mvC[] = " + movementCount[x + X, y + Y, 0]);
//Checks if current adjacent tile subject is in bounds and is not the origin of the search
if (y + Y >= 0 && y + Y <= edgeOfBoard && x + X >= 0 && x + X <= edgeOfBoard && !(Y == 0 && X == 0) && (movementCount[x + X, y + Y, 0] == 99))
{
int[] lowestAdjacent = findLowestAdjacent(x + X, y + Y); //find the lowest adjacent tile
if (lowestAdjacent[0] + 1 <= movementSpeed) //if it is within the movement speed, add it to the matrix
{
movementCount[x + X, y + Y, 0] = lowestAdjacent[0] + 1; //update movement speed for subject tile
movementCount[x + X, y + Y, 1] = lowestAdjacent[1]; //update number of diagonals needed for subject tile
//print();
}
}
}
}
for (int Y = -1; Y <= 1; Y++) //mmove into already checked tiles to recursively check their adjacent tiles
{
for (int X = -1; X <= 1; X++)
{
if (y + Y >= 0 && y + Y <= 15 && x + X >= 0 && x + X <= 15 && !(Y == 0 && X == 0) && (movementCount[x + X, y + Y, 0] != 99) && (movementCount[x + X, y + Y, 0] < movementSpeed))
{
pathfinder(movementSpeed, x + X, y + Y, depth + 1);
}
}
}
}
}
private static int[] findLowestAdjacent(int x, int y) //finds lowest number of movements to get to subject tile (x, y)
{
int[] lowestRtrn = { 99, 0 }; //movement, diagonals
int lowest = 99;
for (int Y = -1; Y <= 1; Y++) //checks each adjacent tile
{
for (int X = -1; X <= 1; X++)
{
if (y + Y >= 0 && y + Y <= edgeOfBoard && x + X >= 0 && x + X <= edgeOfBoard) //ensures it is within bounds
{
int diag = isDiagonalMovement(x, y, x + X, y + Y) ? diagonalMovementIncrease(movementCount[x + X, y + Y, 1] + 1) : 0; //checks whether or not it should be diagonally increased
if ((movementCount[x + X, y + Y, 0] + diag) < lowest) //adds to result if lower than current
{
lowest = movementCount[x + X, y + Y, 0] + diag;
lowestRtrn[1] = movementCount[x + X, y + Y, 1] + (isDiagonalMovement(x, y, x + X, y + Y) ? 1 : 0);
}
}
}
}
lowestRtrn[0] = lowest;
return lowestRtrn;
}
private static int diagonalMovementIncrease(int diagonalMovements) //checks if diagonal is second diagonal (+2 instead of +1)
{
return diagonalMovements % 2 == 0 ? 1 : 0;
}
private static bool isDiagonalMovement(int x, int y, int X, int Y) //checks if (x, y) is diagonal from (X, Y)
{
if (
(x + 1 == X && y + 1 == Y) ||
(x - 1 == X && y + 1 == Y) ||
(x + 1 == X && y - 1 == Y) ||
(x - 1 == X && y - 1 == Y)
)
{
return true;
}
else
{
return false;
}
}`
Code Result
This is the result when printed with a movement speed of 4, starting at 7, 7 on a 15x15 grid (simply for testing purposes, edgeOfBoard = 15)
(99s replaced with " " on the top grid to make it easier to read)
The top grid is the first layer of the third dimension- the amount of tiles it takes to get to that tile.
The bottom grid is the number of diagonals it takes to get to that tile.
The upper left and bottom right quadrants work properly, but the upper right and bottom left do not, which is really stumping me. Can you help me either come up with a new algorithm or fix this one?
You can simplify the business of the diagonal steps being counted as 1.5 steps by storing the number of steps multiplied by 2. So a horizontal or vertical step becomes 2 and a diagonal step becomes 3, and the maximum distance x becomes 2*x+1. This means we don't have to store an additional grid with how many diagonals have been used to get to any tile.
Let's start with this grid, where a value of 99 indicates it is unvisited and empty:
99 99 99 99 99 99 99 99 99 99
99 99 99 99 99 99 99 99 99 99
99 99 99 99 99 99 99 99 99 99
99 99 99 99 99 99 99 99 99 99
99 99 99 99 99 0 99 99 99 99
99 99 99 99 99 99 99 99 99 99
99 99 99 99 99 99 99 99 99 99
99 99 99 99 99 99 99 99 99 99
99 99 99 99 99 99 99 99 99 99
99 99 99 99 99 99 99 99 99 99
We start with the initial position, the tile with coordinates (5,4), on a stack (which is much simpler than using recursion) or a queue (which will be more efficient than a stack in this case). We will then repeatedly take a tile from the queue, check which of its neighbours have a value that is greater than the current tile's value plus two (or three if they are diagonal neighbours), and if so, replace the neighbour's value and add the tile to the queue. After processing all the neighbours of the first tile, we'd have this situation:
99 99 99 99 99 99 99 99 99 99
99 99 99 99 99 99 99 99 99 99
99 99 99 99 99 99 99 99 99 99
99 99 99 99 3 2 3 99 99 99
99 99 99 99 2 0 2 99 99 99
99 99 99 99 3 2 3 99 99 99
99 99 99 99 99 99 99 99 99 99
99 99 99 99 99 99 99 99 99 99
99 99 99 99 99 99 99 99 99 99
99 99 99 99 99 99 99 99 99 99
and these tiles in the queue:
(5,3), (6,3), (6,4), (6,5), (5,5), (4,5), (4,4), (4,3)
When we take the tile (5,3) from the queue, it has value 2, so its neighbour (4,3) would get value 4; however, that tile already has a smaller value 3, so we keep that smaller value, and don't add the tile to the queue. After processing all neighbours of this tile we get:
99 99 99 99 99 99 99 99 99 99
99 99 99 99 99 99 99 99 99 99
99 99 99 99 5 4 5 99 99 99
99 99 99 99 3 2 3 99 99 99
99 99 99 99 2 0 2 99 99 99
99 99 99 99 3 2 3 99 99 99
99 99 99 99 99 99 99 99 99 99
99 99 99 99 99 99 99 99 99 99
99 99 99 99 99 99 99 99 99 99
99 99 99 99 99 99 99 99 99 99
If the maximum distance that can be reached is e.g. 9 (converted from 4 by doing 2*4+1), we keep taking tiles from the queue and processing their neighbours, until no more new tiles have a value of 9 or less, and the queue is empty. The end result is:
99 99 99 99 9 8 9 99 99 99
99 99 9 8 7 6 7 8 9 99
99 99 8 6 5 4 5 6 8 99
99 9 7 5 3 2 3 5 7 9
99 8 6 4 2 0 2 4 6 8
99 9 7 5 3 2 3 5 7 9
99 99 8 6 5 4 5 6 8 99
99 99 9 8 7 6 7 8 9 99
99 99 99 99 9 8 9 99 99 99
99 99 99 99 99 99 99 99 99 99
To translate a distance to a tile from the +2/+3 logic to the +1/+1.5 logic, integer-divide the value in the grid by 2, so that e.g. 9 becomes 4.
You can use the same 2-dimensional grid to also take into account obstacles. You could e.g. mark the empty tiles by 99 and the obstacles by -1. An initial grid:
99 99 99 99 99 99 99 99 99 99
99 99 99 99 99 99 99 99 99 99
99 99 99 99 99 99 99 99 99 99
99 99 99 99 -1 99 99 -1 99 99
99 99 99 99 99 0 99 -1 99 99
99 99 99 99 99 99 99 -1 99 99
99 99 99 99 99 -1 99 99 99 99
99 99 99 99 99 99 99 99 99 99
99 99 99 99 99 99 99 99 99 99
99 99 99 99 99 99 99 99 99 99
would then lead to:
99 99 99 99 9 8 9 99 99 99
99 99 99 8 7 6 7 8 99 99
99 99 8 7 5 4 5 7 9 99
99 9 7 5 -1 2 3 -1 99 99
99 8 6 4 2 0 2 -1 99 99
99 9 7 5 3 2 3 -1 99 99
99 99 8 6 5 -1 5 7 9 99
99 99 9 8 7 8 7 8 99 99
99 99 99 99 9 99 9 99 99 99
99 99 99 99 99 99 99 99 99 99
The details of the main part of the code would then be:
Take a tile from the queue.
Iterate over its neighbours: (-1,-1) (0,-1) (1,-1) (1,0) (1,1) (0,1) (-1,1) (-1,0) and for each (dx,dy) check:
whether coordinates (x+dx, y+dy) are within the grid,
and whether tile (x+dx, y+dy) is not an obstacle,
and whether tile (x+dx, y+dy) is empty or has a value larger than the current tile plus 2 or 3.
If yes to all three conditions, replace the value of (x+dx,y+dy) by the value of the current tile plus 2 or 3.
If the new value of tile (x+dx, y+dy) is less than the maximum distance minus 1, add the tile (x+dx, y+dy) to the queue.
I have a big loop.
I would like split the process through several smaller loops.
So, I use the following code:
class Program
{
static void Main(string[] args)
{
List<string> input = new List<string>();
for (int i = 0; i < 100; i++)
{
input.Add(i.ToString());
}
int take = 2;
List<Task<string>> tasks = new List<Task<string>>();
for (int i = 0; i < 10; i++)
{
// Launch of the tasks
tasks.Add(Task.Run<string>(() => Process(input.Skip(i * take).Take(take).ToList())));
}
Task<string[]> resultTask = Task.WhenAll<string>(tasks.ToArray());
resultTask.Wait();
if (resultTask.Status == TaskStatus.RanToCompletion)
{
foreach (var currentText in resultTask.Result)
{
Console.WriteLine(currentText);
}
}
Console.ReadKey();
}
static int number = 0;
private static string Process(List<string> inputList)
{
foreach (var item in inputList)
{
// The process here for each small loops.
Console.WriteLine(item);
}
return "Thread " + number++;
}
}
So, I take a part of x items from the big loop et I perform the process on each obtained list.
The problem is that the parameter of the method Process is changed inside the method when the code
input.Skip(i * take).Take(take).ToList()
is executed.
I tried by cloning the list but I get the same result.
Why ?
EDIT:
The lists would appear like this:
0 1 2 3 4 5 6 7 8 9
10 11 12 13 14 15 16 17 18 19
20 21 22 23 24 25 26 27 28 29
30 31 32 33 34 35 36 37 38 39
...
90 91 92 93 94 95 96 97 98 99
I have a dynamic matrix and I need to to calculate sum of digits in this way:
0 1 2 3 4 5 6
10 11 12 13 14 15 16
20 21 22 23 24 25 26
30 31 32 33 34 35 36
40 41 42 43 44 45 46
50 51 52 53 54 55 56
60 61 62 63 64 65 66
I can't understand in which way I should compare i and j:
long result = 0;
for (int i = 0; i < len; i++)
{
for (int j = 0; j < len; j++)
{
// only works for diagonal
if (i == j) // should use j - 1 or i - 1?
{
result += matrix[i][j];
}
}
}
no need to scan full matrix:
long result = 0;
for (int i = 0; i < len; i++)
{
result += matrix[i][i]; // diagonal
if (i < len - 1) // stay within array bounds
result += matrix[i][i+1]; // next to diagonal
}
modification without index check on every iteration:
// assign corner value from bottom row to result
long result = matrix[len-1][len-1];
// for each row (except last!) add diagonal and next to diagonal values
for (int i = 0; i < len-1; i++)
result += matrix[i][i] + matrix[i][i+1];
Is it possible to generate a multiplication table (for example, from 1 to 9) with a single for loop?
Yes, using something like this... But why not using two nested loops?
for (int i = 0; i < 9 * 9; ++i)
{
int a = i / 9 + 1;
int b = i % 9 + 1;
Console.WriteLine("{0} * {1} = {2}", a, b, a * b);
}
To generate the multiplication table of 1-9 with a single for loop you could loop 81 time and use the division and modulo operator to get the two operands.
for (int i = 0; i < 9*9; ++i)
{
int a = i / 9 + 1;
int b = i % 9 + 1;
Console.WriteLine($"{a} * {b} = {a * b}");
//Console.WriteLine("{0} * {1} = {2}", a, b, a * b);
}
Note, there must be a better way to construct the output, but I'm not familiar with C#.
Here's a hint for one way to do it.
How can you extract all of the needed multipliers and multiplicands from a single integer from 0 to 81?
try:
Console.WriteLine(" 1 2 3 4 5 6 7 8 9");
for (int i = 1; i<10; i++)
Console.WriteLine(
string.Format("{0}: {1:#0} {2:#0} {3:#0} {4:#0} " +
"{5:#0} {6:#0} {7:#0} {8:#0} {9:#0}",
i, i, 2*i, 3*i, 4*i, 5*i, 6*i, 7*i, 8*i, 9*i));
here, the code for multiplication tables based on our criteria
suppose
Enter a value:2
Enter b value:10
then the output is like 2*1=2 to 2*10=20...
static void Main(string[] args)
{
int a, b, c, d;
Console.WriteLine("enter a value:");
a = Convert.ToInt32(Console.ReadLine());
Console.WriteLine("enter b value:");
b = Convert.ToInt32(Console.ReadLine());
for (d = 1; d <=b; d++)
{
c = a * d;
Console.WriteLine("{0}*{1}={2}",a,d,c);
}
Console.ReadLine();
}
class Program
{
static void Main(string[] args)
{
Console.Write("Enter the value:");
int m = int.Parse(Console.ReadLine());
if (m == 0)
return;
for(int i=1;i<=10;i++)
Console.WriteLine("{0} * {1} ={2}",m,i,m*i);
Console.ReadLine();
}
}
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace ConsoleApplication11
{
class Program
{
int a;
int b;
int c;
public void Accept()
{
Console.WriteLine("enter the no.:");
a = Convert.ToInt32(Console.ReadLine());
}
public void Process()
{
for (int c = 1; c <= 10; c++)
{
b = a * c;
Console.WriteLine("table: {0}", b);
}
Console.ReadLine();
}
public void Display()
{
//Console.WriteLine(a "X" + c +"="b);
}
static void Main(string[] args)
{
Program pr = new Program();
pr.Accept();
pr.Process();
Console.ReadKey();
}
}
}
It is C solution, but you may easily re-write it into whatever language you like.
#include <stdio.h>
void Mult_table(int n)
{
int i;
int a = 0;
int b = 0;
int count = 0;
for (i= 0; i< n*n; ++i)
{
a = i/n + 1;
b = i%n + 1;
printf("%4d ", a*b);
count++;
if(count %n == 0) /*new line*/
{
printf("\n");
}
}
}
Output (if n = 10, but will work with any n):
1 2 3 4 5 6 7 8 9 10
2 4 6 8 10 12 14 16 18 20
3 6 9 12 15 18 21 24 27 30
4 8 12 16 20 24 28 32 36 40
5 10 15 20 25 30 35 40 45 50
6 12 18 24 30 36 42 48 54 60
7 14 21 28 35 42 49 56 63 70
8 16 24 32 40 48 56 64 72 80
9 18 27 36 45 54 63 72 81 90
10 20 30 40 50 60 70 80 90 100