2014-07-24 4 views
-2

에 못생긴 루프 I 소수에 int 요인 코드의 다음과 같은 평화가 :리팩터링 LINQ

private static IEnumerable<int> Factor(int input) 
    { 
     IList<int> result = new List<int>(); 

     while (true) 
     { 
      var theSmallestDivisor = GetTheSmallestDivisor(input); 
      if (theSmallestDivisor == 0) 
      { 
       result.Add(input); 
       return result; 
      } 

      result.Add(theSmallestDivisor); 
      input = input/theSmallestDivisor; 
     } 
    } 

내가 아마도 LINQ를 사용하여, 그것을 개선하는 방법에 대한 힌트를 찾고 있어요입니다.

+3

당신이 무슨 잘못 루프가? 나는 LINQ가 여기에서 돕는 것을 보지 못한다. 당신은 질의를 쓰고 있지 않습니다. – BradleyDotNET

+6

새로운 반짝이 망치 (LINQ) ... 모든 것이 못처럼 보입니다. –

+0

글쎄 LINQ는 이름에도 불구하고 검색어에 관한 것이 아닙니다. 현재 코드는 14 라인입니다. LINQ가 1 라인 밖에 없다면 나는 매우 행복 할 것입니다. –

답변

5

여기 반복자 버전입니다 :

private static IEnumerable<int> Factor(int input) 
{ 
    while (true) 
    { 
     var theSmallestDivisor = GetTheSmallestDivisor(input); 
     if (theSmallestDivisor == 0) 
     { 
      yield return input; 
      yield break; 
     } 

     yield return theSmallestDivisor; 
     input = input/theSmallestDivisor; 
    } 
} 

LINQ는 특정 경우에이 코드는 덜 읽을 수 있도록합니다.

+0

고마워 루카스, 아주 좋아 보인다. 'input = input/theSmallestDivisor' assigment를 제거하고 불변 값을 가진 프로그램처럼 더 기능적으로 사용할 수있는 방법이 있는지 궁금합니다. –

+0

글쎄 ... 완벽한 적의 적이며, 이것은 충분히 좋은 IMO입니다. 기능적 스타일을 원한다면, 재귀를 사용해야합니다. 재귀를 사용하면 스택 오버플로가 발생하기 쉽고, 읽기가 더 어려워지며 재귀를 피하기 위해 복잡한 내용을 수행해야합니다. 오, 그리고 당신은'input/= theSmallestDivisor;를 사용할 수 있습니다; –

-1
public IEnumerable<int> GetFactors(int input) 
{ 
    int first = Primes() 
     .TakeWhile(x => x <= Math.Sqrt(input)) 
     .FirstOrDefault(x => input % x == 0); 
    return first == 0 
      ? new[] { input } 
      : new[] { first }.Concat(GetFactors(input/first)); 
} 
+2

'프라임'은 어디에서 왔습니까? – paqogomez

+0

주어진 예제보다 * better *라고 생각하십니까? 어쩌면 더 똑똑할지 모르지만 실제로는 같은 알고리즘이 아니며 이해/읽기가 매우 어렵습니다. – BradleyDotNET

+0

'프라임()이란 무엇입니까? – Shiva

3

LINQ의 연산자는 대부분 기존 목록에서 새 목록을 생성하도록 설계되었습니다. 예 :

시도한 것처럼 처음부터 목록을 생성하는 것은 아닙니다. 당신이 IEnumerable을 반환하기 때문에

그러나, 당신은뿐만 아니라 그것을 게으른 할 수 있습니다

private static IEnumerable<int> Factor(int input) 
{ 
    while (true) 
    { 
     var theSmallestDivisor = GetTheSmallestDivisor(input); 
     if (theSmallestDivisor == 0) 
     { 
      yield return input; 
      yield break; 
     } 

     yield return theSmallestDivisor; 
     input = input/theSmallestDivisor; 
    } 
}