첨부 실행 코드는 나눔고딕코딩 폰트를 사용합니다.
728x90
반응형
728x170

■ 자연 정렬을 하는 방법을 보여준다.

TestProject.zip
0.00MB

▶ NaturalSortingComparer.cs

using System.Text.RegularExpressions;

namespace TestProject;

/// <summary>
/// 자연 정렬 비교자
/// </summary>
public class NaturalSortingComparer : IComparer<string>
{
    //////////////////////////////////////////////////////////////////////////////////////////////////// Field
    ////////////////////////////////////////////////////////////////////////////////////////// Static
    //////////////////////////////////////////////////////////////////////////////// Private

    #region Field

    /// <summary>
    /// 정규 표현식
    /// </summary>
    private static readonly Regex _regex = new Regex(@"(?<=\D)(?=\d)|(?<=\d)(?=\D)", RegexOptions.Compiled);

    #endregion

    //////////////////////////////////////////////////////////////////////////////////////////////////// Method
    ////////////////////////////////////////////////////////////////////////////////////////// Public

    #region 비교하기 - Compare(source1, source2)

    /// <summary>
    /// 비교하기
    /// </summary>
    /// <param name="source1">소스 문자열 1</param>
    /// <param name="source2">소스 문자열 2</param>
    /// <returns>비교 결과</returns>
    public int Compare(string source1, string source2)
    {
        source1 = source1.ToLower();
        source2 = source2.ToLower();

        if(string.Compare(source1, 0, source2, 0, Math.Min(source1.Length, source2.Length)) == 0)
        {
            if(source1.Length == source2.Length)
            {
                return 0;
            }

            return source1.Length < source2.Length ? -1 : 1;
        }

        string[] tokenArray1 = _regex.Split(source1);
        string[] tokenArray2 = _regex.Split(source2);

        int i = 0;

        while(true)
        {
            int result = ComparePart(tokenArray1[i], tokenArray2[i]);

            if(result != 0)
            {
                return result;
            }

            ++i;
        }
    }

    #endregion

    ////////////////////////////////////////////////////////////////////////////////////////// Private

    #region 부분 비교하기 - ComparePart(source1, source2)

    /// <summary>
    /// 부분 비교하기
    /// </summary>
    /// <param name="source1">소스 문자열 1</param>
    /// <param name="source2">소스 문자열 2</param>
    /// <returns>비교 결과</returns>
    private static int ComparePart(string source1, string source2)
    {
        int value1;
        int value2;

        if(int.TryParse(source1, out value1) && int.TryParse(source2, out value2))
        {
            return value1.CompareTo(value2);
        }

        return source1.CompareTo(source2);
    }

    #endregion
}

 

▶ Program.cs

namespace TestProject;

/// <summary>
/// 프로그램
/// </summary>
class Program
{
    //////////////////////////////////////////////////////////////////////////////////////////////////// Method
    ////////////////////////////////////////////////////////////////////////////////////////// Static
    //////////////////////////////////////////////////////////////////////////////// Private

    #region 프로그램 시작하기 - Main()

    /// <summary>
    /// 프로그램 시작하기
    /// </summary>
    private static void Main()
    {
        string[] sourceArray = new string[]
        {
            "a4",
            "a3",
            "a2",
            "a10",
            "b5",
            "b4",
            "b400",
            "1",
            "C1d",
            "c1d2"
        };

        IOrderedEnumerable<string> targetEnumerable = sourceArray.OrderBy(x => x, new NaturalSortingComparer());

        foreach(string target in targetEnumerable)
        {
            Console.WriteLine(target);
        }
    }

    #endregion
}
728x90
반응형
그리드형(광고전용)
Posted by icodebroker

댓글을 달아 주세요