StreamWriter.Close()가 빈 파일을 생성한 후 전력 손실이 발생하는 이유는 무엇입니까?

StackOverflow https://stackoverflow.com/questions/1427288

  •  07-07-2019
  •  | 
  •  

문제

좋아요, 설명하자면;저는 언제든지 정전이 발생할 수 있는 시스템을 개발 중입니다. 제가 테스트하고 있는 한 지점은 StreamWriter를 사용하여 파일을 작성한 직후입니다.아래 코드:

// Write the updated file back out to the Shell directory.
using (StreamWriter shellConfigWriter =
        new StreamWriter(@"D:\xxx\Shell\Config\Game.cfg.bak"))
{
    for (int i = 0; i < configContents.Count; i++)
    {
        shellConfigWriter.WriteLine(configContents[i]);
    }
    shellConfigWriter.Close();
}

FileInfo gameCfgBackup = new FileInfo(@"D:\xxx\Shell\Config\Game.cfg.bak");
gameCfgBackup.CopyTo(@"D:\xxx\Shell\Config\Game.cfg", true);

의 내용을 씁니다. shellConfigWriter (ㅏ List 문자열)을 임시 저장소로 사용되는 파일로 복사한 다음 원본 위에 복사합니다.이제 이 코드 실행이 완료된 후 전원이 꺼지고 다시 백업을 시작하면 파일이 Game.cfg 존재하고 크기는 정확하지만 완전히 비어 있습니다.처음에는 이것이 하드 드라이브에서 쓰기 캐싱이 활성화되어 있기 때문이라고 생각했지만, 꺼진 상태에서도 여전히 발생합니다(빈도는 낮지만).

어떤 아이디어라도 환영받을 것입니다!

업데이트: 알겠습니다. 제거한 후 .Close() 진술 및 호출 .Flush() 모든 쓰기 작업 후에도 파일은 여전히 ​​비어 있습니다.한 단계 더 나아가 새 파일을 만들기 전에 먼저 원본 파일의 백업을 만든 다음 무결성 검사를 수행할 만큼 충분한 백업을 확보할 수 있지만 이것이 근본적인 문제를 해결하는 데 도움이 될 것이라고 생각하지 않습니다( 파일에 쓰라고 지시하면 파일을 플러시하고 닫습니다.그렇지 않습니다!).

도움이 되었습니까?

해결책

다음을 사용하여 OS가 출력을 버퍼링하지 못하도록 합니다. FileOptions 매개변수 FileStream 객체의 생성자:

    using (Stream fs = new FileStream(@"D:\xxx\Shell\Config\Game.cfg.bak", FileMode.Create, FileAccess.Write, FileShare.None, 0x1000, FileOptions.WriteThrough))
    using (StreamWriter shellConfigWriter = new StreamWriter(fs))
    {
        for (int i = 0; i < configContents.Count; i++)
        {
            shellConfigWriter.WriteLine(configContents[i]);
        }
        shellConfigWriter.Flush();
        shellConfigWriter.BaseStream.Flush();
    }

다른 팁

우선, 전화할 필요가 없습니다. shellConfigWriter.Close() 거기.그만큼 using 성명서가 처리될 것입니다.정전을 방지하기 위해 대신에 하고 싶은 일은 전화입니다. shellConfigWriter.Flush().


업데이트
고려해야 할 또 다른 사항은 정전이 실제로 발생할 수 있는 경우입니다. 어느 시간이 지나면 쓰기 도중에 발생할 수 있으므로 일부 바이트만 파일에 저장됩니다.그걸 막을 방법은 정말 없어요.

이러한 시나리오로부터 보호하기 위한 일반적인 절차는 상태/조건 플래그 파일을 사용하는 것입니다.특정 이름을 가진 0바이트 파일의 파일 시스템에 존재 여부를 사용하여 프로그램이 다시 시작될 때 다시 선택할 위치를 알려줍니다.그런 다음 특정 상태를 트리거하는 파일을 생성하거나 삭제하지 마십시오. 확신하는 해당 상태에 도달했고 이전 단계를 완료했습니다.

여기서의 단점은 때때로 많은 작업을 버리는 것을 의미할 수 있다는 것입니다.그러나 이점은 코드의 기능적 부분이 정상적으로 보인다는 것입니다.시스템을 충분히 견고하게 만들기 위해 수행할 추가 작업이 거의 없습니다.

설정하고 싶으신가요? AutoFlush = true;

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top