문제

.NET (또는 일종의 표준 확장 방법)에 열거에 대한 질문을하는 방법이 있습니까?

예를 들어 현재 항목은 열거의 첫 번째 또는 마지막 항목입니다.

string s = "";

foreach (var person in PeopleListEnumerator) {

  if (PeopleListEnumerator.IsFirstItem) s += "[";

  s += person.ToString();

  if (!PeopleListEnumerator.IsLastItem) s += ",";
  else s += "]";
}
도움이 되었습니까?

해결책

재미를 위해, 열망하는 평가가 필요하지 않고 단일 로컬 변수가있는 일반적인 문제에 대한 해결책 (열거 자 제외).

static class TaggedEnumerableExtensions
{
    public class TaggedItem<T>
    {
        public TaggedItem(T value, bool isFirst, bool isLast)
        {
            IsFirst = isFirst;
            IsLast = isLast;
            Value = value;
        }
        public T Value { get; private set; }
        public bool IsFirst { get; private set; }
        public bool IsLast { get; private set; }
    }
    public static IEnumerable<TaggedItem<T>> ToTaggedEnumerable<T>(this IEnumerable<T> e)
    {
        using (var enumerator = e.GetEnumerator()) {
            if (!enumerator.MoveNext())
                yield break;
            var current = enumerator.Current;
            if (!enumerator.MoveNext()) {
                yield return new TaggedItem<T>(current, true, true);
                yield break;
            } else {
                yield return new TaggedItem<T>(current, true, false);
            }

            for (;;) {
                current = enumerator.Current;
                if (!enumerator.MoveNext()) {
                    yield return new TaggedItem<T>(current, false, true);
                    yield break;
                }
                yield return new TaggedItem<T>(current, false, false);
            }
        }
    }
}

테스트:

class Program
{
    static void Main(string[] args)
    {
        foreach (var item in Enumerable.Range(0, 10).ToTaggedEnumerable()) {
            Console.WriteLine("{0} {1} {2}", item.IsFirst, item.IsLast, item.Value);
        }
    }
}

다른 팁

컬렉션이 목록 인 경우 다음을 수행 할 수 있습니다.

string s = "[" + String.Join(",", PeopleList.ToArray()) + "]";

내가 아는 한에서는 아니다. 그래도 이러한 확장 방법을 직접 작성해보십시오. 또는 다른 곳에서 첫 번째/마지막 항목을 추적하십시오.

Eric Lippert는 a 블로그 게시물 최근에 이러한 종류의 문제에 대해 최근에 문제 설명을 수정하는 방법에 대한 생각과 함께 실제로 원하는 것을보다 정확하게 반영합니다.

당신은 아마도 a를 사용하는 것이 좋습니다 String.join 이 경우 일부 LINQ와 함께 :

String.Join(
  ",",
  (from p in PeopleListEnumerator
  select p.ToString()).ToArray()
)

ienumerable 인터페이스는 주어진 순서로 반환되는 항목을 정의하거나 기대하지 않습니다. 따라서 "첫 번째"의 개념이 항상 적용되는 것은 아닙니다.

그러나이 특정 패턴에 대해 이것은 내가하는 일입니다.

StringBuilder result = new StringBuilder();
result.Append( '[' );

foreach( var person in PeopleListEnumerator )
{
    if( result.Length > 1 )
        result.Append( ',' );
    result.Append( person.ToString() );
}

result.Append( ']' );

Jon Skeet은 썼습니다 스마트 열거 이런 종류의 기능을 제공하기 위해 오해 도서관.

그것은 당신의 구체적인 예가 String.join () 접근법에 의해 가장 잘 해결된다고 말합니다. 장군을 쓰십시오 string Join(this IEnumerable<T>,string) 확장은 어렵지 않으며 성가신 임시 배열에 의지하지 않고 더 이상 상황에서 사용할 수 있습니다.

LINQ를 사용하면 다음을 수행 할 수 있습니다.

string s = 
    string.Format("[{0}]", string.Join(",",PeopleListEnumerator.Select(p => p.ToString()).ToArray()));

예를 들어 "Bool First"로컬 변수를 정의하고 사용합니다.

string s = "[";
bool first = true;

foreach (var person in PeopleListEnumerator) {

  if (first)
    first = false;
  else
    s += ",";
  s += person.ToString();
}
s += "]";

이 코드는 당신이 정말로 달성하고자하는 것과 밀접하게 일치합니다.

StringBuilder s = new StringBuilder("[");
string delimiter = "";

foreach (var person in PeopleListEnumerator) {  
  s.Append(delimiter).Append(person.ToString());
  delimiter = ",";
}

return s.Append("]").ToString();

내가이 고양이를 피부를 피우는 방식 (예, 많은 방법이 있습니다)은 다음과 같습니다.

StringBuilder sb = new StringBuilder();

foreach (var person in PeopleListEnumerator )
{
    sb.AppendFormat(",{0}", person.ToString());
}

string s = "[" + sb.ToString().Substring(1) + "]";

도움이 되었기를 바랍니다...

.NET에서 열거는 값을 제외하고는 질서 개념이 없습니다. 첫 번째 및 마지막 열거를 원한다면 첫 번째와 마지막 값이 무엇인지 명시 적으로 정의하는 것이 좋습니다. 다음 열거는 다음의 예입니다.

public enum PlayerType : byte
{
    Starter = byte.MinValue,
    RegularPlayer = 1,
    BenchWarmer = 2,
    Closer = byte.MaxValue
}

그런 다음 다음과 유사한 것을 표현할 수 있습니다.

List<byte> values = new List<byte>((byte[])Enum.GetValues(typeof(PlayerType)));

PlayerType starter = (PlayerType)values.Min();
PlayerType closer = (PlayerType)values.Max();
라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top