Tworzenie pustego pliku w C #


186

Jaki jest najprostszy / kanoniczny sposób utworzenia pustego pliku w C # / .NET?

Najprostszym sposobem, jaki udało mi się znaleźć do tej pory, jest:

System.IO.File.WriteAllLines(filename, new string[0]);

Odpowiedzi:


384

Użycie just File.Createpozostawi plik otwarty, co prawdopodobnie nie jest tym, czego chcesz.

Możesz użyć:

using (File.Create(filename)) ;

To trochę dziwne, pamiętaj. Zamiast tego możesz użyć nawiasów klamrowych:

using (File.Create(filename)) {}

Lub po prostu zadzwoń Disposebezpośrednio:

File.Create(filename).Dispose();

Tak czy inaczej, jeśli zamierzasz użyć tego w więcej niż jednym miejscu, prawdopodobnie powinieneś rozważyć zapakowanie go w metodę pomocniczą, np.

public static void CreateEmptyFile(string filename)
{
    File.Create(filename).Dispose();
}

Należy pamiętać, że dzwoniąc Disposebezpośrednio zamiast używać usingoświadczenie naprawdę nie robi dużej różnicy tutaj o ile mogę powiedzieć - tylko w ten sposób, że mógł dokonać różnica jest jeśli wątek zostały przerwane między wywołaniu File.Createi wywołaniu Dispose. Jeśli ten warunek wyścigu istnieje, podejrzewam, że istniałby również w usingwersji, gdyby wątek został przerwany na samym końcu File.Createmetody, tuż przed zwróceniem wartości ...


8
Zabawny. Właśnie napisałem ten sam kod około 5 minut temu. Zrobiłem File.Create (nazwa pliku) .Close (); Ten sam
trudny

2
Mój kod był używany using (File.Create(filename)) ;, ale uwielbiam prostotęFile.Create(filename).Dispose();
Vadim

@BrianGenisio: Zrobiłem ten sam kod około 5 minut temu! Właśnie googlowałem, żeby zobaczyć, jak zrobili to inni programiści. Teraz używam File.Create(filename).Dispose();zamiast.
Jack

1
@ user3791372: Close()zwolni również zasoby. Close()tylko połączenia Dispose- patrz github.com/dotnet/coreclr/blob/master/src/mscorlib/src/System/…
Jon Skeet

1
Może nie być oczywiste, że jeśli plik już istnieje i nie jest tylko do odczytu, zawartość pliku zostanie zastąpiona. Aby tego uniknąć, użyjusing (new FileStream(filename, FileMode.CreateNew)) { }
Phil Haselden

34
File.WriteAllText("path", String.Empty);

lub

File.CreateText("path").Close();

2
Używając pierwszego, plik ma 3 bajty: kodowanie. Używając sekundy plik ma 0 bajtów (naprawdę jest pusty).
Fil

1
@Fil: Jesteś pewien? Dokumentacja mówi, że File.WriteAllText(string, string)używa „kodowania UTF-8 bez znaku Byte-Order Mark (BOM)” . Jeśli nadal go widzisz, byłby to błąd w WriteAllText lub jego dokumentacji, którą warto zgłosić.
Heinzi

Pamiętam, że próbowałem. Może to był stary błąd poprzedniej wersji .Net? Plik nie jest pusty, jeśli wyraźnie podam kodowanie UTF8 (lub Unicode lub coś innego): <File.WriteAllText („c: \ del.txt”, String.Empty, System.Text.Encoding.UTF8);>
Fil

1
@Fil, Encoding.UTF8zwraca koder, który wyprowadza znak Byte Order Mark (BOM). Możesz użyć, new UTF8Encoding(false)aby uzyskać koder UTF8, który nie generuje BOM.
Daniel Crabtree

1
Nie wiem, czy WriteAllTextnaprawdę zachowuje się inaczej w poprzedniej wersji .NET. Jednak dla większej pewności po prostu pomiń część kodującą i użyj File.WriteAllBytes(path, new byte[] { });zamiast tego.
Jürgen Steinblock

20
System.IO.File.Create(@"C:\Temp.txt");

Jak zauważyli inni, powinieneś pozbyć się tego obiektu lub zawinąć go w pustą instrukcję using.

using (System.IO.File.Create(@"C:\Temp.txt"));

4
nie lepiej pozbyć się obiektu? np .: using (System.IO.File.Create (
ścieżka pliku

@kentaromiura: Dokładnie moje myśli, stąd moja odpowiedź :)
Jon Skeet

4

Możesz powiązać metody ze zwróconym obiektem, dzięki czemu możesz natychmiast zamknąć plik, który właśnie otworzyłeś w jednej instrukcji.

File.Open("filename", FileMode.Create).Close();

4

Aby uniknąć przypadkowego zastąpienia istniejącego pliku, użyj:

using (new FileStream(filename, FileMode.CreateNew)) {}

... i obsłuż wyjątek IOException, który pojawi się, jeśli plik już istnieje.

File.Create, co jest sugerowane w innych odpowiedziach, zastąpi zawartość, jeśli plik już istnieje. W prostych przypadkach można to złagodzić za pomocą File.Exists(). Jednak coś bardziej niezawodnego jest konieczne w scenariuszach, w których wiele wątków i / lub procesów próbuje jednocześnie utworzyć pliki w tym samym folderze.


2

Nieco powszechnym przypadkiem użycia do utworzenia pustego pliku jest wywołanie czegoś innego w innym procesie przy braku bardziej wyrafinowanej komunikacji procesu. W takim przypadku pomocne może być tworzenie pliku bez użycia atomu z punktu widzenia świata zewnętrznego (szczególnie jeśli rzecz, która zostanie uruchomiona, usunie plik, aby „wykorzystać” wyzwalacz).

Może więc pomóc stworzyć niepotrzebną nazwę (Guid.NewGuid.ToString ()) w tym samym katalogu, co plik, który chcesz utworzyć, a następnie wykonać File.Move z nazwy tymczasowej na pożądaną nazwę. W przeciwnym razie kod uruchamiany, który sprawdza istnienie pliku, a następnie usuwa wyzwalacz, może uruchomić się w warunkach wyścigu, w których plik jest usuwany przed całkowitym zamknięciem.

Posiadanie pliku tymczasowego w tym samym katalogu (i systemie plików) zapewnia atomowość, jakiej możesz potrzebować. To daje coś takiego.

public void CreateEmptyFile(string path)
{
    string tempFilePath = Path.Combine(Path.GetDirectoryName(path),
        Guid.NewGuid.ToString());
    using (File.Create(tempFilePath)) {}
    File.Move(tempFilePath, path);
}

0

Path.GetTempFileName () utworzy pusty plik o unikalnej nazwie i zwróci do niego ścieżkę.

Jeśli chcesz kontrolować ścieżkę, ale chcesz uzyskać losową nazwę pliku, możesz użyć GetRandomFileName, aby po prostu zwrócić ciąg nazwy pliku i użyć go z opcją Utwórz

Na przykład:

string fileName=Path.GetRandomFileName();
File.Create("custom\\path\\" + fileName);

IMHO GetTempFileName () jest całkowicie błędnie nazwany.
kay.herzam

Dlaczego dokładnie ta odpowiedź nie jest pomocna?
Crippledsmurf

5
Jest to nieprzydatne z dwóch powodów: 1. Pytanie nie dotyczy pytania o wygenerowanie losowej nazwy pliku, więc to rozprasza. 2. Plik nie zostanie zamknięty, co oznacza, że ​​jeśli później spróbujesz otworzyć inny program zapisujący pliki lub przenieść plik, zakończy się niepowodzeniem.
Rzeka Satya,

Rozumiem twoje uwagi, ale: 1. Wszystkie pliki wymagają nazwy. To było proste. wygodny sposób, aby uzyskać taki, który prawdopodobnie nie koliduje z niczym 2. Pytanie zadawane o tworzenie plików, które w danym pytaniu minimalnie zarządza plikiem, nie jest już ściśle częścią tworzenia, więc pominąłem to dla ze względu na prostotę i skoncentrowanie odpowiedzi na pytaniu
Crippledsmurf,
Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.