답변:
목록을 사용하지 않으려면 다음을 수행하십시오.
var foos = new List<Foo>(array);
foos.RemoveAt(index);
return foos.ToArray();
실제로 테스트하지 않은이 확장 방법을 시도 할 수 있습니다.
public static T[] RemoveAt<T>(this T[] source, int index)
{
T[] dest = new T[source.Length - 1];
if( index > 0 )
Array.Copy(source, 0, dest, 0, index);
if( index < source.Length - 1 )
Array.Copy(source, index + 1, dest, index, source.Length - index - 1);
return dest;
}
그리고 그것을 다음과 같이 사용하십시오 :
Foo[] bar = GetFoos();
bar = bar.RemoveAt(2);
배열의 특성상 길이는 변경할 수 없습니다. 배열 항목을 추가하거나 삭제할 수 없습니다.
한 요소보다 짧은 새 배열을 작성하고 삭제하려는 요소를 제외하고 이전 항목을 새 배열로 복사해야합니다.
따라서 배열 대신 List를 사용하는 것이 좋습니다.
List<mydatatype> array = new List<mydatatype>(arrayofmydatatype)
var myList = myArray.ToList();
의 Enumerable.ToList()
메소드를 사용하십시오 System.Linq
.
이 방법을 사용하여 객체 배열에서 요소를 제거합니다. 내 상황에서 배열의 길이는 작습니다. 따라서 배열이 큰 경우 다른 솔루션이 필요할 수 있습니다.
private int[] RemoveIndices(int[] IndicesArray, int RemoveAt)
{
int[] newIndicesArray = new int[IndicesArray.Length - 1];
int i = 0;
int j = 0;
while (i < IndicesArray.Length)
{
if (i != RemoveAt)
{
newIndicesArray[j] = IndicesArray[i];
j++;
}
i++;
}
return newIndicesArray;
}
LINQ 단선 솔루션 :
myArray = myArray.Where((source, index) => index != 1).ToArray();
1
이 예에서, 원래의 질문에 따라, 제 2 요소 (와 -이 예에서 요소의 인덱스를 제거하는 1
C # 제로 어레이 인덱스에서 두 번째 요소이다).
보다 완전한 예 :
string[] myArray = { "a", "b", "c", "d", "e" };
int indexToRemove = 1;
myArray = myArray.Where((source, index) => index != indexToRemove).ToArray();
해당 스 니펫을 실행 한 후의 값은 myArray
입니다 { "a", "c", "d", "e" }
.
이것은 다음과 같은 배열 인스턴스를 사용하여 다른 배열에 복사하지 않고 .Net 3.5에서 배열 요소를 삭제하는 방법입니다 Array.Resize<T>
.
public static void RemoveAt<T>(ref T[] arr, int index)
{
for (int a = index; a < arr.Length - 1; a++)
{
// moving elements downwards, to fill the gap at [index]
arr[a] = arr[a + 1];
}
// finally, let's decrement Array's size by one
Array.Resize(ref arr, arr.Length - 1);
}
ref
를 호출 할 때 사용해야 합니다 Resize
. 배열 인스턴스의 길이는 고정되어 있으며 변경할 수 없습니다.
다음은 .NET 프레임 워크 버전 1.0에서 작동하며 일반 유형이 필요하지 않은 이전 버전 입니다.
public static Array RemoveAt(Array source, int index)
{
if (source == null)
throw new ArgumentNullException("source");
if (0 > index || index >= source.Length)
throw new ArgumentOutOfRangeException("index", index, "index is outside the bounds of source array");
Array dest = Array.CreateInstance(source.GetType().GetElementType(), source.Length - 1);
Array.Copy(source, 0, dest, 0, index);
Array.Copy(source, index + 1, dest, index, source.Length - index - 1);
return dest;
}
이것은 다음과 같이 사용됩니다 :
class Program
{
static void Main(string[] args)
{
string[] x = new string[20];
for (int i = 0; i < x.Length; i++)
x[i] = (i+1).ToString();
string[] y = (string[])MyArrayFunctions.RemoveAt(x, 3);
for (int i = 0; i < y.Length; i++)
Console.WriteLine(y[i]);
}
}
평소처럼, 나는 파티에 늦었다 ...
이미 존재하는 멋진 솔루션 목록에 다른 옵션을 추가하고 싶습니다. =)
나는 이것이 Extensions의 좋은 기회라고 생각합니다.
참조 :
http://msdn.microsoft.com/en-us/library/bb311042.aspx
그래서 우리는 정적 클래스와 그 안에 메소드를 정의합니다.
그 후에 확장 된 방법 인 willy-nilly를 사용할 수 있습니다. =)
using System;
namespace FunctionTesting {
// The class doesn't matter, as long as it's static
public static class SomeRandomClassWhoseNameDoesntMatter {
// Here's the actual method that extends arrays
public static T[] RemoveAt<T>( this T[] oArray, int idx ) {
T[] nArray = new T[oArray.Length - 1];
for( int i = 0; i < nArray.Length; ++i ) {
nArray[i] = ( i < idx ) ? oArray[i] : oArray[i + 1];
}
return nArray;
}
}
// Sample usage...
class Program {
static void Main( string[] args ) {
string[] myStrArray = { "Zero", "One", "Two", "Three" };
Console.WriteLine( String.Join( " ", myStrArray ) );
myStrArray = myStrArray.RemoveAt( 2 );
Console.WriteLine( String.Join( " ", myStrArray ) );
/* Output
* "Zero One Two Three"
* "Zero One Three"
*/
int[] myIntArray = { 0, 1, 2, 3 };
Console.WriteLine( String.Join( " ", myIntArray ) );
myIntArray = myIntArray.RemoveAt( 2 );
Console.WriteLine( String.Join( " ", myIntArray ) );
/* Output
* "0 1 2 3"
* "0 1 3"
*/
}
}
}
내가 한 방법은 다음과 같습니다.
public static ElementDefinitionImpl[] RemoveElementDefAt(
ElementDefinition[] oldList,
int removeIndex
)
{
ElementDefinitionImpl[] newElementDefList = new ElementDefinitionImpl[ oldList.Length - 1 ];
int offset = 0;
for ( int index = 0; index < oldList.Length; index++ )
{
ElementDefinitionImpl elementDef = oldList[ index ] as ElementDefinitionImpl;
if ( index == removeIndex )
{
// This is the one we want to remove, so we won't copy it. But
// every subsequent elementDef will by shifted down by one.
offset = -1;
}
else
{
newElementDefList[ index + offset ] = elementDef;
}
}
return newElementDefList;
}
private int[] removeFromArray(int[] array, int id)
{
int difference = 0, currentValue=0;
//get new Array length
for (int i=0; i<array.Length; i++)
{
if (array[i]==id)
{
difference += 1;
}
}
//create new array
int[] newArray = new int[array.Length-difference];
for (int i = 0; i < array.Length; i++ )
{
if (array[i] != id)
{
newArray[currentValue] = array[i];
currentValue += 1;
}
}
return newArray;
}
다음은 기존 답변 중 일부를 기반으로 생성 된 도우미 메서드 모음입니다. 최대의 이상성을 위해 참조 매개 변수와 함께 확장 및 정적 메소드를 모두 사용합니다.
public static class Arr
{
public static int IndexOf<TElement>(this TElement[] Source, TElement Element)
{
for (var i = 0; i < Source.Length; i++)
{
if (Source[i].Equals(Element))
return i;
}
return -1;
}
public static TElement[] Add<TElement>(ref TElement[] Source, params TElement[] Elements)
{
var OldLength = Source.Length;
Array.Resize(ref Source, OldLength + Elements.Length);
for (int j = 0, Count = Elements.Length; j < Count; j++)
Source[OldLength + j] = Elements[j];
return Source;
}
public static TElement[] New<TElement>(params TElement[] Elements)
{
return Elements ?? new TElement[0];
}
public static void Remove<TElement>(ref TElement[] Source, params TElement[] Elements)
{
foreach (var i in Elements)
RemoveAt(ref Source, Source.IndexOf(i));
}
public static void RemoveAt<TElement>(ref TElement[] Source, int Index)
{
var Result = new TElement[Source.Length - 1];
if (Index > 0)
Array.Copy(Source, 0, Result, 0, Index);
if (Index < Source.Length - 1)
Array.Copy(Source, Index + 1, Result, Index, Source.Length - Index - 1);
Source = Result;
}
}
현명한 성능, 그것은 괜찮지 만 아마도 향상 될 수 있습니다. Remove
에 의존 IndexOf
하고를 호출하여 제거하려는 각 요소에 대해 새 배열이 작성됩니다 RemoveAt
.
IndexOf
원래 배열을 반환 할 필요가 없으므로 유일한 확장 방법입니다. New
특정 유형의 여러 요소를 허용하여 해당 유형의 새 배열을 생성합니다. 다른 모든 메소드는 원래 배열을 참조로 허용해야하므로 결과는 이미 내부적으로 발생하므로 나중에 결과를 할당 할 필요가 없습니다.
Merge
두 배열을 병합 하는 방법을 정의했습니다 . 그러나 Add
실제 배열과 여러 개별 요소를 전달 하여 메소드로 이미 수행 할 수 있습니다 . 따라서 Add
다음 두 가지 방법으로 두 요소 세트를 결합 할 수 있습니다.
Arr.Add<string>(ref myArray, "A", "B", "C");
또는
Arr.Add<string>(ref myArray, anotherArray);
나는이 기사가 열 살이되었을 것이므로 아마 죽었을 것입니다. 그러나 여기에 내가 시도한 것이 있습니다 :
System.Linq에있는 IEnumerable.Skip () 메서드를 사용하십시오 . 배열에서 선택한 요소를 건너 뛰고 선택한 개체를 제외한 모든 항목 만 포함하는 다른 배열 복사본을 반환합니다. 그런 다음 제거하려는 모든 요소에 대해 반복하고 변수에 저장하십시오.
예를 들어, 5 개의 숫자를 가진 "Sample"(int [] 유형)이라는 배열이있는 경우. 우리는 두 번째 것을 제거하고 싶기 때문에 "Sample.Skip (2);" 두 번째 숫자를 제외하고 동일한 배열을 반환해야합니다.
첫 번째 단계
배열을 목록으로 변환해야합니다. 이렇게 확장 메서드를 작성할 수 있습니다
// Convert An array of string to a list of string
public static List<string> ConnvertArrayToList(this string [] array) {
// DECLARE a list of string and add all element of the array into it
List<string> myList = new List<string>();
foreach( string s in array){
myList.Add(s);
}
return myList;
}
두 번째 단계
목록을 배열로 다시 변환하는 확장 메소드 작성
// convert a list of string to an array
public static string[] ConvertListToArray(this List<string> list) {
string[] array = new string[list.Capacity];
array = list.Select(i => i.ToString()).ToArray();
return array;
}
마지막 단계
최종 방법을 작성하되 코드 쇼와 같은 배열로 다시 변환하기 전에 색인에서 요소를 제거해야합니다.
public static string[] removeAt(string[] array, int index) {
List<string> myList = array.ConnvertArrayToList();
myList.RemoveAt(index);
return myList.ConvertListToArray();
}
예제 코드는 내 블로그 에서 찾을 수 있습니다 . 계속 추적하십시오.
.ToArray()
및 List<T>
... 기존의 서열을 얻어 생성자
System.Collections.ObjectModel.Collection<Foo>
.