Easiest way to Rotate a List in c#
You could implement it as a queue. Dequeue and Enqueue the same value.
**I wasn't sure about performance in converting a List to a Queue, but people upvoted my comment, so I'm posting this as an answer.
C#, Rotate a List to the Right by specified places
Here is a approache with Linq
with Skip()
and Take()
.
List<int> iList = new List<int>() { 20, 30, 40, 50, 60, 70 };
int rotate = 3;
List<int> lResult = iList.Skip(rotate).Concat(iList.Take(rotate)).ToList();
another approach with a simple loop
int[] items = new int[] { 20, 30, 40, 50, 60, 70 };
int[] result = new int[items.Length];
int rotate = 3;
for (int i = 0; i < items.Length; i++)
{
result[i] = items[(i+rotate)% items.Length];
}
What is the best way to endlessly rotate 3 items in a list in C#
Ideally this would be achieved with a linked list, the advantage is that only node references are disconnected and no internal copying is needed. A C# Queue
is actually based a linked list, so this is a fairly appropriate data structure.
However, this can also be done with a List
at a small cost. When you do an Insert
or Remove
, it internally calls Array.Copy
and although it's still O(n), providing it doesn't fail a capacity check there is no allocation and is extremely efficient and optimized.
Example Extensions
public static void RotateDown<T>(this IList<T> source)
{
// ideally you would remove first to save a potential capacity expansion
source.Add(source[0]);
source.RemoveAt(0);
}
public static void RotateUp<T>(this IList<T> source)
{
// ideally you would remove first to save a potential capacity expansion
source.Insert(0,source[^1]);
source.RemoveAt(source.Count-1);
}
Test
var list = new List<int>() {1, 2, 3, 4, 5};
Console.WriteLine(string.Join(", ",list));
list.RotateUp();
Console.WriteLine(string.Join(", ", list));
list.RotateUp();
Console.WriteLine(string.Join(", ", list));
list.RotateDown();
Console.WriteLine(string.Join(", ", list));
list.RotateDown();
Console.WriteLine(string.Join(", ", list));
Output
1, 2, 3, 4, 5
5, 1, 2, 3, 4
4, 5, 1, 2, 3
5, 1, 2, 3, 4
1, 2, 3, 4, 5
Note : Methods lack any range checking. Also ideally this would target a less derived interface, though it's only an example.
How to efficiently rotate an array?
This will use less memory in most cases as the second array is only as big as the shift.
public static void Main(string[] args)
{
int[] n = { 1, 2, 3, 4, 5 };
LeftShiftArray(n, 4);
Console.WriteLine(String.Join(",", n));
}
public static void LeftShiftArray<T>(T[] arr, int shift)
{
shift = shift % arr.Length;
T[] buffer = new T[shift];
Array.Copy(arr, buffer, shift);
Array.Copy(arr, shift, arr, 0, arr.Length - shift);
Array.Copy(buffer, 0, arr, arr.Length - shift, shift);
}
How to zip or rotate a variable number of lists?
You can roll your own ZipMany instance which manually iterates each of the enumerations. This will likely perform better on larger sequences than those using GroupBy
after projecting each sequence:
public static IEnumerable<TResult> ZipMany<TSource, TResult>(
IEnumerable<IEnumerable<TSource>> source,
Func<IEnumerable<TSource>, TResult> selector)
{
// ToList is necessary to avoid deferred execution
var enumerators = source.Select(seq => seq.GetEnumerator()).ToList();
try
{
while (true)
{
foreach (var e in enumerators)
{
bool b = e.MoveNext();
if (!b) yield break;
}
// Again, ToList (or ToArray) is necessary to avoid deferred execution
yield return selector(enumerators.Select(e => e.Current).ToList());
}
}
finally
{
foreach (var e in enumerators)
e.Dispose();
}
}
How to rotate a list of strings along an axis?
It sounds like you are describing something like this:
private void Form1_Paint(object sender, PaintEventArgs e)
{
foreach (var str in data)
{
e.Graphics.TranslateTransform(str.X, str.Y);
e.Graphics.RotateTransform(30);
e.Graphics.DrawString(str.StringName, mFont, new SolidBrush(Color.Black), new Point(0, 0));
e.Graphics.ResetTransform();
}
}
This snippet first translates, then rotates, draws the string at the transformed origin, and then resets. Both strings are rotated at the same angle on the same X axis, but originate from different points.
Related Topics
How to Compare Two Objects in Unit Test
How to Share Data Between Different Threads in C# Using Aop
Irregular Shaped Windows Form (C#)
C#: Throwing Custom Exception Best Practices
C# - Elegant Way of Partitioning a List
Windows Phone 8: Media File Access
How to Protect This Function from SQL Injection
Twoway-Bind View's Dependencyproperty to Viewmodel's Property
Assemblytitle' Attribute in the .Net Framework
How to Implement the Equivalent of SQL In() Using .Net
Deserialize JSON to Anonymous Object
How to Avoid Page Refresh After Button Click Event in Asp.Net