System.Runtime.CompilerServices.MethodImplAttribute
속성은 데코 레이팅 된 메서드를 처리하는 방법에 대한 힌트를 JIT 컴파일러에 제공하는 데 사용할 수 있습니다. 특히 옵션 MethodImplOptions.AggressiveInlining
은 가능한 경우 영향을받는 메소드를 인라인하도록 컴파일러에 지시합니다. 불행하게도 F # 컴파일러는 일리노이 생성시이 속성을 무시하는 것처럼 보입니다.MethodImplOptions.AggressiveInlining을 F # 함수에 적용
예 : 다음 C# 코드
[MethodImpl(MethodImplOptions.AggressiveInlining)]
public static int Inc(int x) => x + 1;
는
.method public hidebysig static int32 Inc(int32 x) cil managed aggressiveinlining
{
.maxstack 8
IL_0000: ldarg.0
IL_0001: ldc.i4.1
IL_0002: add
IL_0003: ret
}
참고 "aggressiveinlining"플래그로 변환된다.
이 F # 코드 그러나
[<MethodImpl(MethodImplOptions.AggressiveInlining)>]
let inc x = x + 1
는
.method public static int32 inc(int32 x) cil managed
{
.maxstack 8
IL_0000: nop
IL_0001: ldarg.0
IL_0002: ldc.i4.1
IL_0003: add
IL_0004: ret
}
없음 "aggressiveinlining"가된다. 또한 적절한 클래스의 정적 및 비 정적 메서드 (type ...
)에 특성을 적용하려고 시도했지만 결과는 동일합니다.
내가 그렇게
type Dummy =
member self.Item
with [<MethodImpl(MethodImplOptions.AggressiveInlining)>] get x = x + 1
처럼, 사용자 정의 인덱서에 적용 그러나 나는 "그가 동일한 지 어떤지 잘 모르겠어요하지만 결과 IL은 ...
.method public hidebysig specialname instance int32 get_Item(int32 x) cil managed
{
.custom instance void [mscorlib]System.Runtime.CompilerServices.MethodImplAttribute::.ctor(valuetype [mscorlib]System.Runtime.CompilerServices.MethodImplOptions) = (01 00 00 01 00 00 00 00)
.maxstack 8
IL_0000: nop
IL_0001: ldarg.1
IL_0002: ldc.i4.1
IL_0003: add
IL_0004: ret
}
경우 aggressiveinling "플래그를 생성합니다.
동작이 바람직합니까? F # 컴파일러의 버그입니까?
(참고 : 나는 F 번호 inline
키워드 알고 있어요,하지만 그건 단지 내 도서관,하지 C#을 소비자의 F 번호 클라이언트에 적용됩니다.)
AFAIK이 속성은 JIT에서 사용합니다. 즉, 메서드가 인라인되어야 함을 나타냅니다. 따라서 올바른 경우 기계 코드 생성을 확인해야합니다.노트; JIT를 실행하는 디버거 에서처럼 .NET에서 디스 어셈블리를 보는 것만 큼 간단하지 않습니다. 어 : 공격적이지 않습니다. – FuleSnabel
Awww, 무슨 뜻인지 알 겠어. 일리노이 메타 데이터가 누락 된 것 같습니다. 나중에 이것을 확인하겠습니다. – FuleSnabel
'PreserveSig','Synchronized' 및'NoInlining' 만 존중합니다 - [IlxGen.fs]의'ComputeMethodImplAttribs' (https://github.com/Microsoft/visualfsharp/blob/master/src/fsharp)를보십시오. /IlxGen.fs) – kvb