상세 컨텐츠

본문 제목

[C#] int, char, byte 등등의 배열 Array 복사,초기화 등등 관련

본문

반응형

 

 

 

 

 

 

 

=======================

=======================

=======================

 

 

 

 

 

 

 

출처: https://thinkerodeng.tistory.com/146

 

  1. Byte[] array = new Byte[64];  
  2.   
  3. Array.Clear(array, 0, array.Length);  


출처: https://thinkerodeng.tistory.com/146 [Thinker]

 

 

 

 

=======================

=======================

=======================

 

 

 

 

 

출처: https://docs.microsoft.com/ko-kr/dotnet/api/system.array.clear?view=netframework-4.7.2

 

 

Array.Clear(Array, Int32, Int32) Method

정의

배열의 각 요소 형식의 기본값으로 요소의 범위를 설정합니다.

C#
public static void Clear (Array array, int index, int length);

매개 변수

array
Array

포함된 요소를 지울 배열입니다.

index
Int32

지울 요소 범위의 시작 인덱스입니다.

length
Int32

지울 요소의 개수입니다.

예외

array가 null인 경우

index가 array의 하한값보다 작습니다.

또는 length가 0보다 작은 경우

또는 index 및 length 합계가 array의 크기보다 큽니다.

예제

다음 예제에서는 Clear 1 차원, 2 차원 및 3 차원 배열에서 정수 값을 다시 설정 하는 방법입니다.

C#
using System;  class Example {     public static void Main()     {         Console.WriteLine("One dimension (Rank=1):");         int[] numbers1 = { 1, 2, 3, 4, 5, 6, 7, 8, 9 };          for (int i = 0; i < 9; i++)         {             Console.Write("{0} ", numbers1[i]);         }         Console.WriteLine();         Console.WriteLine();          Console.WriteLine("Array.Clear(numbers1, 2, 5)");         Array.Clear(numbers1, 2, 5);          for (int i = 0; i < 9; i++)         {             Console.Write("{0} ", numbers1[i]);         }         Console.WriteLine();         Console.WriteLine();          Console.WriteLine("Two dimensions (Rank=2):");         int[,] numbers2 = { { 1, 2, 3 }, { 4, 5, 6 }, { 7, 8, 9 } };          for (int i = 0; i < 3; i++)         {             for (int j = 0; j < 3; j++)             {                 Console.Write("{0} ", numbers2[i, j]);             }             Console.WriteLine();         }          Console.WriteLine();         Console.WriteLine("Array.Clear(numbers2, 2, 5)");         Array.Clear(numbers2, 2, 5);          for (int i = 0; i < 3; i++)         {             for (int j = 0; j < 3; j++)             {                 Console.Write("{0} ", numbers2[i, j]);             }             Console.WriteLine();         }          Console.WriteLine("Three dimensions (Rank=3):");         int[, ,] numbers3 = {{{1, 2}, {3, 4}},                              {{5, 6}, {7, 8}},                              {{9, 10}, {11, 12}}};          for (int i = 0; i < 2; i++)         {             for (int j = 0; j < 2; j++)             {                 for (int k = 0; k < 2; k++)                 {                     Console.Write("{0} ", numbers3[i, j, k]);                 }                 Console.WriteLine();             }             Console.WriteLine();         }          Console.WriteLine("Array.Clear(numbers3, 2, 5)");         Array.Clear(numbers3, 2, 5);          for (int i = 0; i < 2; i++)         {             for (int j = 0; j < 2; j++)             {                 for (int k = 0; k < 2; k++)                 {                     Console.Write("{0} ", numbers3[i, j, k]);                 }                 Console.WriteLine();             }             Console.WriteLine();         }     } } /*  This code example produces the following output:  *   * One dimension (Rank=1):  * 1 2 3 4 5 6 7 8 9  *   * Array.Clear(numbers1, 2, 5)  * 1 2 0 0 0 0 0 8 9  *   * Two dimensions (Rank=2):  * 1 2 3  * 4 5 6  * 7 8 9  *   * Array.Clear(numbers2, 2, 5)  * 1 2 0  * 0 0 0  * 0 8 9  *   * Three dimensions (Rank=3):  * 1 2  * 3 4  *   * 5 6  * 7 8  *   * Array.Clear(numbers3, 2, 5)  * 1 2  * 0 0  *   * 0 0  * 0 8  */ 

다음 예제에서는 정의 TimeZoneTime 구조를 포함 하는 TimeZoneInfo 필드 및 DateTimeOffset 필드. 그런 다음 호출 하는 Clear 의 2 요소 배열의 요소가 하나를 선택 취소 하는 방법 TimeZoneTime 값입니다. 기본값으로 지워진 요소 값을 설정 하는 메서드를 TimeZoneInfo 개체 이며, null, 및의 기본 값을 DateTimeOffset 개체 이며, DateTimeOffset.MinValue합니다.

C#
using System;  public struct TimeZoneTime {    private DateTimeOffset dt;    private TimeZoneInfo tz;        public TimeZoneTime(DateTimeOffset dateTime, TimeZoneInfo timeZone)    {       dt = dateTime;       tz = timeZone;    }     public DateTimeOffset DateTime     { get { return dt; } }        public TimeZoneInfo TimeZone     { get { return tz; } } }  public class Example {    public static void Main()    {       // Declare an array with two elements.       TimeZoneTime[] timeZoneTimes = { new TimeZoneTime(DateTime.Now, TimeZoneInfo.Local),                                        new TimeZoneTime(DateTime.Now, TimeZoneInfo.Utc) };          foreach (var timeZoneTime in timeZoneTimes)          Console.WriteLine("{0}: {1:G}",                             timeZoneTime.TimeZone == null ? "<null>" : timeZoneTime.TimeZone.ToString(),                             timeZoneTime.DateTime);       Console.WriteLine();              Array.Clear(timeZoneTimes, 1, 1);       foreach (var timeZoneTime in timeZoneTimes)          Console.WriteLine("{0}: {1:G}",                             timeZoneTime.TimeZone == null ? "<null>" : timeZoneTime.TimeZone.ToString(),                             timeZoneTime.DateTime);    } } // The example displays the following output: //       (UTC-08:00) Pacific Time (US & Canada): 1/20/2014 12:11:00 PM //       UTC: 1/20/2014 12:11:00 PM //        //       (UTC-08:00) Pacific Time (US & Canada): 1/20/2014 12:11:00 PM //       <null>: 1/1/0001 12:00:00 AM 

설명

이 메서드는 배열의 각 요소에에서 요소 형식의 기본값으로 다시 설정합니다. 참조 형식의 요소를 설정 하는 것 (포함 String 요소)를 null, 다음 표에 표시 된 기본값으로 값 형식의 요소를 가져오거나 설정 합니다.

형식
Boolean false
모든 정수 계열 및 부동 소수점 숫자 형식 0 (영)
DateTime DateTime.MinValue
다른 값 형식 형식 필드의 기본값

다양 한 다차원 배열의 요소 줄 바꿈을 행 마다 지워집니다.

이 메서드는만; 요소의 값을 지웁니다. 요소 자체는 삭제 되지 않습니다. 배열 크기가 고정 따라서 요소 추가 하거나 제거할 수 없습니다.

이 메서드는 O (n) 작업, 여기서 n 는 length합니다.

 

 

 

=======================

=======================

=======================

 

 

 

 

출처: https://blanedil.tistory.com/10

 

 

일반적인 객체처럼 배열 또한 참조값이기 때문에 복사를 해도 참조값만 복사되는 문제점이 있다.

배열은 메모리 차원의 복사가 필요하기 때문에 C#에서는 다음과 같은 두가지 복사방법을 제공하고 있다.

 

* Array.Copy()를 이용하는 방법

 - 배열의 일부분 복사

* Clone()함수를 이용하는 방법

 - 배열의 전체 복사(배열의 메모리 차원의 복사)

 

Array.Copy(source, target, 2);

 - source배열을 target 배열로 source배열의 첫부분부터 2개만 값 복사

 

Array.Copy(source, 0, target, 2, 3);

 - source 배열의 0번째부터 3개를 target 배열의 2번째부터 값 복사

 

using System;

 

namespace ArrayCopyTest

{

    class ArrayCopyTest

    {

        static void Main(string[] args)

        {

            int[] myOriginal = new int[] { -1, -3, -5, -7, -9 };

            int[] myCopy = { 2, 4, 6, 8, 10 };

            Array.Copy(myOriginal, 0, myCopy, 2, 3);

            for (int i = 0; i < myCopy.Length; i++)

            {

                Console.Write("myCopy[" + i + "]=" + myCopy[i] + '\t');

            }

        }

    }

}



출처: https://blanedil.tistory.com/10 [죽도록하면 죽는다]

 

 

 

 

=======================

=======================

=======================

 

 

 

 

반응형

 

 

728x90

 

 

 

출처: https://codingcoding.tistory.com/354

 

 

C# byte 배열 빠르게 합치기 (바이트 array)

 

C#에서 바이트 배열 합치기를 시도할 때, System.Buffer.BlockCopy가 System.Array.Copy보다 빠릅니다. 아래는 10 바이트 배열 3개를 1백만 번 반복한 결과로 함수의 수행 시간을 측정한 결과입니다.

 

바이트 배열 : System.Array.Copy - 0.2187556초

바이트 배열 : System.Buffer.BlockCopy - 0.1406286초

IEnumerable<byte> : C# yield operator - 0.0781270초

IEnumerable<byte> : LINQ's Concat<> - 0.0781270초

 

byte 배열 크기를 100개로 늘리고 다시 테스트한 결과는 아래.

 

바이트 배열 : System.Array.Copy - 0.2812554초

바이트 배열 : System.Buffer.BlockCopy - 0.2500048초

IEnumerable<byte> : C# yield operator - 0.0625012초

IEnumerable<byte> : LINQ's Concat<> - 0.0781265초

 

 

byte 배열 크기를 1,000개로 늘리고 다시 테스트한 결과는 아래.

 

바이트 배열 : System.Array.Copy - 1.0781457초

바이트 배열 : System.Buffer.BlockCopy - 1.0156445초

IEnumerable<byte> : C# yield operator - 0.0625012초

IEnumerable<byte> : LINQ's Concat<> - 0.0781265초

 

마지막으로 배열 크기를 1백만으로 늘리고 복사 과정을 4,000번 반복한 결과는 아래.

 

바이트 배열 : System.Array.Copy - 13.4533833초

바이트 배열 : System.Buffer.BlockCopy - 13.1096267초

IEnumerable<byte> : C# yield operator - 0초

IEnumerable<byte> : LINQ's Concat<> - 0초

 

즉, 새로운 바이트 배열이 필요하면,

 

1
2
3
4
5
byte[] rv = new byte[a1.Length + a2.Length + a3.Length];
 
System.Buffer.BlockCopy(a1, 0, rv, 0, a1.Length);
System.Buffer.BlockCopy(a2, 0, rv, a1.Length, a2.Length);
System.Buffer.BlockCopy(a3, 0, rv, a1.Length + a2.Length, a3.Length);
cs

 

만약 IEnumerable<byte>을 사용하면 LINQ의 Concat<>을 사용할 수 있습니다. yield 보다 약간 느리지만, 더 간결합니다.

 

 

1
IEnumerable<byte> rv = a1.Concat(a2).Concat(a3);
cs

 

 

 

닷넷 3.5를 사용할 경우 System.Buffer.BlockCopy()를 아래처럼 사용할 수 있습니다.

 

1
2
3
4
5
6
7
8
9
10
11
private byte[] Combine(params byte[][] arrays)
{
    byte[] rv = new byte[arrays.Sum(a => a.Length)];
    int offset = 0;
 
    foreach (byte[] array in arrays) {
        System.Buffer.BlockCopy(array, 0, rv, offset, array.Length);
        offset += array.Length;
    }
    return rv;
}
cs

 

참고 - 위의 블록을 사용하려면 맨 위에 다음과 같은 네임 스페이스를 추가해야 합니다.

 

using System.Linq;

 

마지막으로, 1백만 개 크기의 byte 배열을 만들고 4,000번 반복 테스트를 했습니다. 중간에 전체 데이터를 확인하는 루틴을 넣었죠. 결과는 아래와 같습니다.

 

바이트 배열 : System.Array.Copy - 78.20550510초

바이트 배열 : System.Buffer.BlockCopy - 77.89261900초

IEnumerable<byte> : C# yield operator - 551.7150161초

IEnumerable<byte> : LINQ's Concat<> - 448.1804799초

 

이 포스트의 핵심은 데이터 생성과 사용의 효율성을 이해하는 것입니다. 단순히 기능이 완성되었다는 것을 넘어 효율적으로 구성되었는지를 확인해야 하죠.



출처: https://codingcoding.tistory.com/354 [코딩 기록]

 

 

 

=======================

=======================

=======================

 

 

 

 

출처: https://blanedil.tistory.com/10

 

일반적인 객체처럼 배열 또한 참조값이기 때문에 복사를 해도 참조값만 복사되는 문제점이 있다.

배열은 메모리 차원의 복사가 필요하기 때문에 C#에서는 다음과 같은 두가지 복사방법을 제공하고 있다.

 

* Array.Copy()를 이용하는 방법

 - 배열의 일부분 복사

* Clone()함수를 이용하는 방법

 - 배열의 전체 복사(배열의 메모리 차원의 복사)

 

Array.Copy(source, target, 2);

 - source배열을 target 배열로 source배열의 첫부분부터 2개만 값 복사

 

Array.Copy(source, 0, target, 2, 3);

 - source 배열의 0번째부터 3개를 target 배열의 2번째부터 값 복사

 

using System;

 

namespace ArrayCopyTest

{

    class ArrayCopyTest

    {

        static void Main(string[] args)

        {

            int[] myOriginal = new int[] { -1, -3, -5, -7, -9 };

            int[] myCopy = { 2, 4, 6, 8, 10 };

            Array.Copy(myOriginal, 0, myCopy, 2, 3);

            for (int i = 0; i < myCopy.Length; i++)

            {

                Console.Write("myCopy[" + i + "]=" + myCopy[i] + '\t');

            }

        }

    }

}

 
다음으로 배열을 메모리 차원에서 복사하기 위한 Clone()함수에 대해 알아보자.
Copy()함수는 메모리가 생성되어 있는 배열에 값을 복사해주었지만 Clone()함수를 사용하면 메모리를 통째로 복사할 수 있다.
Object형을 반환하기 때문에 다운캐스팅 해서 사용해야 한다.
 
using System;
 
namespace ArrayCopyTest2
{
    class ArrayCopyTest2
    {
        static void Main(string[] args)
        {
            int[] myOriginal = new int[] { 1, 2, 3, 4 };
            int[] myCopy = (int[])myOriginal.Clone();
            for (int i = 0; i < myCopy.Length; i++)
            {
                Console.Write("myCopy[" + i + "]:" + myCopy[i] + '\t');
            }
        }
    }
}



출처: https://blanedil.tistory.com/10 [죽도록하면 죽는다]

 

 

 

 

=======================

=======================

=======================

 

 

 

 

반응형


관련글 더보기

댓글 영역