Эффективный способ записи в TXT-файл из консольной программы - PullRequest
4 голосов
/ 30 сентября 2008

Какой самый эффективный способ записи в журнал (.txt) из консольной программы на C # и .NET 2.2? Моя программа зацикливается несколько раз, всегда выводя разные данные в зависимости от того, что хочет пользователь, поэтому я ищу наиболее эффективный способ достижения этого.

Я знаю, что всегда могу снова открыть поток и затем закрыть его, но каждый раз, когда я это делаю, он записывает только одну строку, а затем в следующий раз (несколько секунд спустя) программа перезапускается и требует повторной записи. На мой взгляд, это не очень благоприятно для ресурсов.

Я использую несколько потоков, у всех из которых есть выходные данные, которые я хочу записать (открытие / закрытие одного и того же файла или доступ к одному и тому же файлу в разных потоках может быть плохим). «Содержит ссылку на потоковую запись, которая автоматически очищается» звучит как хорошая идея, однако я не знаю, как это сделать.

Ответы [ 6 ]

16 голосов
/ 30 сентября 2008

Рассмотрите возможность использования log4net :

инструмент, помогающий программисту выводить лог-операторы для различных выходных целей ... Мы сохранили структуру, сходную по духу с оригинальным log4j, используя при этом новые возможности в среде выполнения .NET. Для получения дополнительной информации о log4net см. Документ features ...

3 голосов
/ 30 сентября 2008

Вы можете подключиться к инфраструктуре трассировки, которая является частью CLR. Используя простой класс, такой как: http://www.chaosink.co.uk/files/tracing.zip, вы можете выборочно регистрировать диагностическую информацию. Чтобы использовать его, добавьте класс в ваше приложение. Создайте сопротивление трейсера в своем классе, например:

private Tracing trace = new Tracing("My.Namespace.Class");

и позвоните, используя:

MyClass()
{
    trace.Verbose("Entered MyClass");
    int x = 12;
    trace.Information("X is: {0}", x);
    trace.Verbose("Leaving MyClass");
}

В встроенной платформе трассировки есть 4 уровня информации:

Verbose - для регистрации потока программы

Информация - для регистрации конкретной информации, представляющей интерес для мониторов

Предупреждение - для регистрации недопустимого состояния или восстанавливаемого исключения

Ошибка - для регистрации неисправимого исключения или состояния

Чтобы получить доступ к информации из вашего приложения, добавьте в app.config (или web.config) следующее:

<system.diagnostics>
    <trace autoflush="false" indentsize="4">
        <listeners>
            <add name="myListener" type="System.Diagnostics.TextWriterTraceListener" initializeData="c:\mylogfile.log" />
        </listeners>
    </trace>
    <switches>
        <add name="My.Namespace.Class" value="4"/>      
    </switches>
</system.diagnostics>

Вы также можете присоединить слушателей для публикации в журнале событий или в любом другом месте, которое вас интересует. Более подробную информацию о структуре трассировки можно найти по адресу:

http://msdn.microsoft.com/en-us/library/ms733025.aspx

3 голосов
/ 30 сентября 2008

Я принимаю снижение производительности при открытии и закрытии каждый раз, когда пишу строку. Это решение о надежности. Если вы держите все в памяти и у вас возникли серьезные сбои, у вас вообще нет информации журнала, чтобы помочь устранить неполадки. Если это вас не беспокоит, то хранение в памяти определенно обеспечит лучшую производительность.

2 голосов
/ 30 сентября 2008

Я согласен с использованием log4net.

Но если вам действительно нужно что-то простое, рассмотрите возможность использования синглтона, содержащего ссылку на StreamWriter, который автоматически сбрасывается в каждой строке записи.

Таким образом, вы сохраняете файл открытым на протяжении всей сессии, избегая закрытия / открытия, не рискуя потерять данные журнала в случае серьезного сбоя.

0 голосов
/ 01 октября 2008

Каркасы журналирования, такие как log4net, должны правильно обрабатывать многопоточность.

Может также быть полезный совет: регистрация значительно загрязняет код, делая его менее читабельным. Рассматривали ли вы использование аспекта для добавления функциональности регистрации в код во время компиляции? См. Эту статью для примера .

0 голосов
/ 30 сентября 2008

Простой подход заключается в предоставлении TextWriterTraceListener и добавлении его в коллекцию TraceListeners в классе Trace. Это автоматически запишет все ваши вызовы Trace.Write ... в соответствующий файл.

...