C #에서 정수에 대한 나누기와 모듈로를 어떻게 계산할 수 있습니까?


85

C #에서 정수에 대한 나누기와 모듈로를 어떻게 계산할 수 있습니까?


15
이것은 너무 기본이 될 수도 있지만 ... 진짜 질문

2
연산자가 C #에서 모듈러스 연산자 가 아닌 이유에 대한 관련 게시물 및 반드시 읽어야하는 블로그 입니다 . %
RBT

답변:


123

이런 종류의 질문을하기 전에 MSDN 설명서 를 확인하십시오 .

두 정수를 나눌 때 결과는 항상 정수입니다. 예를 들어 7/3의 결과는 2입니다. 7/3의 나머지를 확인하려면 나머지 연산자 ( % )를 사용합니다.

int a = 5;
int b = 3;

int div = a / b; //quotient is 1
int mod = a % b; //remainder is 2

9
%는 모듈러스가 아닌 나머지를 반환합니다. 그것들은 같은 것이 아니며 비정상적인 경우 (예 : 음수 인덱스)를 다룰 때 문제를 일으킬 수 있습니다. 그러나 예를 들어 약한 양의 인덱서의 매 10 번째 반복을 찾을 때 모듈러스 연산자처럼 사용할 수 있습니다. 실제 계수를 계산하는 방법을 설명해 주시겠습니까?
Cor_Blimey 2012 년

1
사실, 나는 이와 같은 게시물을 읽고 내 응용 프로그램에 문제가있었습니다. :)
apocalypse

1
... 정확히 선언의 시점 무엇 ab당신이 그들을 사용하지 않을 경우는? : D
leviathanbadger

1
아마도 사용자가 (나와 같은) DivRem 함수를 검색하고 있었기 때문에 질문이 언뜻보기에 사소하지 않을 수 있습니다. 감사합니다 @danodonovan
Tancredi

1
대답은 다른 사람들도 지적 했듯이이 대답이 주장하는 것처럼 간단하지 않으며 디버깅하기 어려운 실수로 이어질 수 있습니다. 참조 /programming/10065080/mod-explanation
SansWit

88

도 있습니다 Math.DivRem

quotient = Math.DivRem(dividend, divisor, out remainder);

2
이것은 하나의 함수에서 몫과 나머지를 제공하기 때문에 내 의견으로는 정답이어야합니다. 어떤 접근법이 더 잘 수행되는지 확신 할 수 없습니다 ( "a / b"를 사용하여 몫을 얻은 다음 "a % b"를 사용하여 나머지 또는 Math.DivRem을 얻음).이 접근법은 확실히 읽기가 훨씬 더 좋습니다 (제 경우에는 몫과 나머지를 모두 알고 있음)-감사합니다!
이고르

2
@Igor 감사합니다. 원래 질문에 답했을 때이 기능은 존재하지 않았습니다! 그러나 함수의 존재로 인해 문서 확인에 대한 as-cii의 발언이 약간 어리석게 보입니다 .... :)
danodonovan

5
혼동을 피하기 위해 Math.DivRem한 번의 작업으로 div와 mod를 계산하지 않습니다. 도우미 함수일 뿐이며 소스 코드는 정확히 다음과 같습니다 public static int DivRem(int a, int b, out int result) { result = a%b; return a/b; }..
NightElfik

9
@NightElfik 구현은 향후 변경 될 수 있습니다, 그리고 런타임이 연결되지 않은 것보다 최적화를 위해 메소드 호출을 식별하기가 쉽습니다 divrem지침
kbolino

6
@kbolino 즉 좋은 예측은 이후의 있다 변경 분할 및 빼기, 적어도 .NET 핵심에. RyuJIT에는 단일 x86 div 명령어를 사용하기위한 추가 최적화가 계획되어 있지만 JIT 변경은 개별적으로 사용되는 경우 %/연산자 도 감지해야합니다 .

15

재미있는 사실!

'모듈러스'연산은 다음과 같이 정의됩니다.

a % n ==> a - (a/n) * n

참고 : 모듈 식 산술

그렇게 할 수 는 FAR 느린 % 연산자에 내장 된보다지라도, 당신은 자신의 롤 :

public static int Mod(int a, int n)
{
    return a - (int)((double)a / n) * n;
}

편집 : 와우, 원래 여기에 오히려 잘못되었습니다. 저를 잡은 @joren에게 감사드립니다.

이제 여기서는 C #의 division + cast-to-int가 Math.Floor(즉, 분수를 삭제함) 과 동일하다는 사실에 의존하고 있지만 "진정한"구현은 대신 다음과 같습니다.

public static int Mod(int a, int n)
{
    return a - (int)Math.Floor((double)a / n) * n;
}

실제로 다음을 사용하여 %와 "실제 계수"의 차이를 확인할 수 있습니다.

var modTest =
    from a in Enumerable.Range(-3, 6)
    from b in Enumerable.Range(-3, 6)
    where b != 0
    let op = (a % b)
    let mod = Mod(a,b)
    let areSame = op == mod
    select new 
    { 
        A = a,
        B = b,
        Operator = op, 
        Mod = mod, 
        Same = areSame
    };
Console.WriteLine("A      B     A%B   Mod(A,B)   Equal?");
Console.WriteLine("-----------------------------------");
foreach (var result in modTest)
{
    Console.WriteLine(
        "{0,-3} | {1,-3} | {2,-5} | {3,-10} | {4,-6}", 
        result.A,
        result.B,
        result.Operator, 
        result.Mod, 
        result.Same);
}

결과 :

A      B     A%B   Mod(A,B)   Equal?
-----------------------------------
-3  | -3  | 0     | 0          | True  
-3  | -2  | -1    | -1         | True  
-3  | -1  | 0     | 0          | True  
-3  | 1   | 0     | 0          | True  
-3  | 2   | -1    | 1          | False 
-2  | -3  | -2    | -2         | True  
-2  | -2  | 0     | 0          | True  
-2  | -1  | 0     | 0          | True  
-2  | 1   | 0     | 0          | True  
-2  | 2   | 0     | 0          | True  
-1  | -3  | -1    | -1         | True  
-1  | -2  | -1    | -1         | True  
-1  | -1  | 0     | 0          | True  
-1  | 1   | 0     | 0          | True  
-1  | 2   | -1    | 1          | False 
0   | -3  | 0     | 0          | True  
0   | -2  | 0     | 0          | True  
0   | -1  | 0     | 0          | True  
0   | 1   | 0     | 0          | True  
0   | 2   | 0     | 0          | True  
1   | -3  | 1     | -2         | False 
1   | -2  | 1     | -1         | False 
1   | -1  | 0     | 0          | True  
1   | 1   | 0     | 0          | True  
1   | 2   | 1     | 1          | True  
2   | -3  | 2     | -1         | False 
2   | -2  | 0     | 0          | True  
2   | -1  | 0     | 0          | True  
2   | 1   | 0     | 0          | True  
2   | 2   | 0     | 0          | True  

"이제 저는 C #의 정수 나누기가 Math.Floor (즉, 분수를 떨어 뜨림)와 동일하다는 사실에 의존하고 있습니다."-하지만 그렇지 않습니다. Integer divison은 0으로 반올림되고 Math.Floor는 음의 무한대로 반올림됩니다.
Joren 2013 년

죄송합니다 @Joren 있지만 -이 작업을 실행하려고하지 : Enumerable.Range(0, 10).Select(x => (double)x / 10.0).Select(x => (int)x).ToList().ForEach(x => Console.WriteLine(x));- 모두 0을
JerKimball

2
먼저 정수 나누기에 대해 이야기하고 있습니다. 부동 소수점 나누기를 수행 한 다음 정수로 캐스트하는 것은 관련이 없습니다 (동일한 결과를 제공하더라도). 둘째, 10으로 나누고 정수 부분으로 자른 후 0과 9 사이의 정수가 0이 아닌 다른 값을 줄 것으로 예상하는 이유를 잘 모르겠습니다. 그 결과 1이 나오면 0에서 멀어 지거나 양의 무한대 로 반올림 됩니다 . 셋째, 0으로 반올림하는 것과 양수에 대해 음의 무한대로 반올림하는 것에 는 차이없으므로 문제를 해결하지도 않습니다.
Joren

Math.Floor(-10.0 / 3.0)하고 -10 / 3있습니다 하지 같은 일.
Joren

@joren 아, 여기에 연결이 끊어진 것이 보입니다. 아니요, 정수 나누기를 수행하지 않고 이중 나누기를 수행하고 결과를 정수로 캐스팅합니다. 매우 다릅니다.
JerKimball 2013 년

14

분할은 /연산자를 사용하여 수행됩니다 .

result = a / b;

모듈로 나누기는 %연산자를 사용하여 수행됩니다 .

result = a % b;

1
+1 : 편리하게 유형을 생략하면 더 나은 대답이됩니다. :-) 4.0에서도 System.Numeric.BigInteger와 함께 작동한다고 생각합니다.

5
%-> Cor_Blimey가 말했듯이 모듈러스가 아닌 나머지를 반환합니다. 예 : (-5 % 3) == -2 [C #], -5 mod 3 = 1 [wolframalpha.com].
apocalypse

2
참고 : Modulo는 Modulus와 동일하지 않습니다. Modulo는 나머지이고 Modulus는 절대 값입니다.
라이언

-4

사용자로부터 두 개의 정수를 읽습니다. 그런 다음 나머지와 몫을 계산 / 표시합니다.

// When the larger integer is divided by the smaller integer
Console.WriteLine("Enter integer 1 please :");
double a5 = double.Parse(Console.ReadLine());
Console.WriteLine("Enter integer 2 please :");
double b5 = double.Parse(Console.ReadLine());

double div = a5 / b5;
Console.WriteLine(div);

double mod = a5 % b5;
Console.WriteLine(mod);

Console.ReadLine();
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.