문제: 다음 달을 계산하시오
int year = 2024;
int month = 11;
절차적 접근법
// year first
year += month / 12;
month = month % 12 + 1;
Console.WriteLine($"year first: {year} / {month}");
// month first
month = month % 12 + 1;
year += month / 12;
Console.WriteLine($"month first: {year} / {month}");
결과
year first: 2024 / 12
month first: 2025 / 12
year 와 month 의 계산 순서가 중요함 => 에러 유발 요소
Tuple 사용
// year left
(year, month) = (year + month / 12, month % 12 + 1);
Console.WriteLine($"year left: {year} / {month}");
// month left
(month, year) = (month % 12 + 1, year + month / 12);
Console.WriteLine($"month left: {year} / {month}");
결과
year left: 2024 / 12
month left: 2024 / 12
year 와 month 의 계산 순서가 중요하지 않음. => 안전
4개의 좋아요
suwoo
2
전에 튜플 관련해서 IL 까보니까
보통은 임시 변수 하나를 생성해서 계산을 하고
후에 대입 하는 식으로 하더라고요.
linqpad의 IL+Native로 구경해보면…
int year = 2024;
int month = 11;
// year left
(year, month) = (year + month / 12, month % 12 + 1);
Console.WriteLine($"year left: {year} / {month}");
이게
int year = 2024;
int month = 11;
int num = year + month / 12;
month = month % 12 + 1;
year = num;
DefaultInterpolatedStringHandler defaultInterpolatedStringHandler = new DefaultInterpolatedStringHandler (14, 2);
defaultInterpolatedStringHandler.AppendLiteral ("year left: ");
defaultInterpolatedStringHandler.AppendFormatted (year);
defaultInterpolatedStringHandler.AppendLiteral (" / ");
defaultInterpolatedStringHandler.AppendFormatted (month);
Console.WriteLine (defaultInterpolatedStringHandler.ToStringAndClear ());
IL_0001 ldc.i4 E8 07 00 00 // 2024
IL_0006 stloc.0 // year
IL_0007 ldc.i4.s 0B // 11
IL_0009 stloc.1 // month
IL_000A ldloc.0 // year
IL_000B ldloc.1 // month
IL_000C ldc.i4.s 0C // 12
IL_000E div
IL_000F add
IL_0010 ldloc.1 // month
IL_0011 ldc.i4.s 0C // 12
IL_0013 rem
IL_0014 ldc.i4.1
IL_0015 add
IL_0016 stloc.1 // month
IL_0017 stloc.0 // year
IL_0018 ldloca.s 02
IL_001A ldc.i4.s 0E // 14
IL_001C ldc.i4.2
IL_001D call DefaultInterpolatedStringHandler..ctor
IL_0022 ldloca.s 02
IL_0024 ldstr "year left: "
IL_0029 call DefaultInterpolatedStringHandler.AppendLiteral (String)
IL_002E nop
IL_002F ldloca.s 02
IL_0031 ldloc.0 // year
IL_0032 call DefaultInterpolatedStringHandler.AppendFormatted<Int32> (Int32)
IL_0037 nop
IL_0038 ldloca.s 02
IL_003A ldstr " / "
IL_003F call DefaultInterpolatedStringHandler.AppendLiteral (String)
IL_0044 nop
IL_0045 ldloca.s 02
IL_0047 ldloc.1 // month
IL_0048 call DefaultInterpolatedStringHandler.AppendFormatted<Int32> (Int32)
IL_004D nop
IL_004E ldloca.s 02
IL_0050 call DefaultInterpolatedStringHandler.ToStringAndClear ()
IL_0055 call Console.WriteLine (String)
이렇게 변환된다고 하네요!
3개의 좋아요
tkm
4
(x, y) = (y, x);
이것만 보아도 뭐… 절차적이지 않은건 당연한 것 같아요
2개의 좋아요