У меня есть метод расширения, который выглядит следующим образом:
//[MethodImpl(MethodImplOptions.NoOptimization)]
public static IEnumerable<char> TakeWhile(this BinaryReader reader, Func<int, bool> condition)
{
while (condition(reader.PeekChar()))
{
char c = reader.ReadChar();
yield return c;
}
}
Я использую этот метод при анализе файла с BinaryReader, чтобы пропустить блок пробельных символов, среди прочего. Я обнаружил, что JIT-компилятор оптимизирует его, когда я называю это так:
// Skip white space
this.reader.TakeWhile(IsWhiteSpace);//.FirstOrDefault();
Я попытался добавить атрибут [MethodImpl (...)], чтобы дать указание компилятору JIT не оптимизировать метод, но он не работает. Теперь, очевидно, я мог бы написать еще одну реализацию этого, которая манипулирует позицией основного буфера потока, но из любопытства я хотел бы знать, почему это так.
Единственный способ предотвратить оптимизацию, который я нашел, - это использовать результаты IEnumerable (например, с помощью вызова .FirstOrDefault (), как указано выше) или скопировать код в вызывающий метод. Я пытался предотвратить оптимизацию вызывающих методов, используя MethodImplAttribute, но это не работает. Как ни странно, оптимизация полностью отключена в сборке Debug, поэтому она не должна происходить ни в одной ситуации. Кто-нибудь знает другой способ предотвращения оптимизации?