77

I have a string array like this.

string[] queries with data more than one string.

I want to skip the last string from the element and take the remaining. I have come up with

var remStrings = queries.Reverse().Skip(1).Take(queries.Length - 1);

Is there a better alternative to this?

dotcoder
  • 2,828
  • 10
  • 34
  • 50

7 Answers7

129
var remStrings = queries.Take(queries.Length - 1);

No need to Reverse and Skip. Just take one less element than there are in the array.

If you really wanted the elements in the reverse order, you could tack on a .Reverse() to the end.

Justin Niessner
  • 242,243
  • 40
  • 408
  • 536
39

For anyone finding this now...

With the upcoming support for ranges and indices C# 8 and .NET Core 3.0 you can simply write

var remStrings = queries[..^1]

This is short for

var remStrings = queries[0..^1]

This works by converting the 0 and 1 to indices (System.Index), with the ^ being the marker (actually an operator) to index from the end of a sequence. From these indices a range (System.Range) is then generates which can then be used to access the array. (See https://learn.microsoft.com/en-us/dotnet/csharp/whats-new/csharp-8#indices-and-ranges)

Currently this only works in the preview version of .NET Core 3.0

user1781290
  • 2,674
  • 22
  • 26
15

Microsoft's Reactive Extensions' Team has the Interactive Extensions (NuGet "System.Interactive") that lets you do this:

var remStrings = queries.SkipLast(1);
Enigmativity
  • 113,464
  • 11
  • 89
  • 172
12

Why not just have:

var remStrings = queries.Take(queries.Length-1);

Which will return them in the same order.

Append .Reverse() to swap the order if that's a necessary requirement:

var remStrings = queries.Take(queries.Length-1).Reverse();
ChrisF
  • 134,786
  • 31
  • 255
  • 325
2

This answer from a related post is also worth mentioning as it elegantly applies to any IEnumerable in a single pass, without the need to know its number of elements beforehand.

Community
  • 1
  • 1
Erwin Mayer
  • 18,076
  • 9
  • 88
  • 126
0

Edited: You could effectively replace your array with the same array minus the last element with the following line or code:

queries = queries.Take(queries.Length - 1).ToArray();

If you would like to create a method that does this for you, then you could use the following:

public static string[] TrimLastElement(string[] arr) {
    return arr.Take(arr.Length - 1).ToArray();
}

And implement it in your code like so:

queries = TrimLastElement(queries);
FrostyOnion
  • 856
  • 7
  • 10
  • There are no variables of type `var`. `var` is just a keyword that instructs the compiler to infer the type. Your line of code is identical to `var temp = temp.Take(temp.Length - 1).ToArray();`. – Enigmativity Jun 26 '17 at 04:36
  • I understand what you wanna say, it should be like `temp = temp.Take(temp.Length - 1).ToArray();` – ainasiart Sep 07 '17 at 18:47
  • Thank you for your feedback! My post has now been edited. – FrostyOnion Sep 29 '17 at 01:53
0

Maybe this is an indirect solution. However, a different approach without using extension.

// Convert string array to generic list
List<string> queries = new[] { "a", "b", "c", "d", "e" }.ToList();

var lastElement = queries.LastOrDefault();
var takeAllExceptLastElement = queries.Take(queries.LastIndexOf(lastElement));
        
Console.WriteLine(string.Join(",", takeAllExceptLastElement));
Umut D.
  • 1,746
  • 23
  • 24