Praca z dużymi plikami w VIM

108

Próbowałem otworzyć ogromny (~ 2 GB) plik w VIM, ale się zaciął. Właściwie nie muszę edytować pliku, po prostu sprawnie skaczę.

Jak mogę pracować z bardzo dużymi plikami w VIM?

hoju
źródło
1
Oto podobne pytanie .
GeoAvila
5
Vim powinien być w porządku, o ile :set binarynajpierw ...
ephemient,
1
To dobry cel dla nowego systemu plików fuse! splitfs czy coś w tym stylu ... Lubię to!
rodrigo
1
Za późno ... to już istnieje: sourceforge.net/projects/joinsplitfs
rodrigo.
5
Potrzebujesz pagera, a nie redaktora! Zobacz odpowiedź Jima poniżej.
Lester Cheung

Odpowiedzi:

85

Miałem dziś do edycji plik 12 GB. Wtyczka vim LargeFile nie działała dla mnie. Nadal zużywał całą moją pamięć, a następnie wyświetlał komunikat o błędzie :-(. Nie mogłem też użyć hexedit, ponieważ nie może niczego wstawić, po prostu nadpisać. Oto alternatywne podejście:

Podziel plik, edytuj części, a następnie ponownie go połączysz. Jednak nadal potrzebujesz dwa razy więcej miejsca na dysku.

  • Wyszukaj coś otaczającego linię, którą chcesz edytować:

    grep -n 'something' HUGEFILE | head -n 1
    
  • Wyodrębnij ten zakres pliku. Powiedz, że wiersze, które chcesz edytować, znajdują się w wierszach 4 i 5. Następnie wykonaj:

    sed -n -e '4,5p' -e '5q' HUGEFILE > SMALLPART
    
    • Ta -nopcja jest wymagana do powstrzymania domyślnego zachowania seda podczas wypisywania wszystkiego
    • 4,5p drukuje linie 4 i 5
    • 5q przerywa sed po przetwarzaniu linii 5
  • Edytuj SMALLPARTza pomocą swojego ulubionego edytora.

  • Połącz plik:

    (head -n 3 HUGEFILE; cat SMALLPART; sed -e '1,5d' HUGEFILE) > HUGEFILE.new 
    
    • tj .: wybierz wszystkie wiersze przed edytowanymi wierszami z OGROMNEGO PLIKU (który w tym przypadku jest 3 górnymi wierszami), połącz go z edytowanymi wierszami (w tym przypadku wiersze 4 i 5) i użyj tego połączonego zestawu wierszy do zastąpienia odpowiednik (w tym przypadku górne 5 wierszy) w HUGEFILE i zapisz to wszystko do nowego pliku.

    HUGEFILE.newbędzie teraz edytowanym plikiem, możesz usunąć oryginał HUGEFILE.

Florian
źródło
30

To powracające pytanie od wielu lat. (Liczby się zmieniają, ale koncepcja jest taka sama: jak przeglądać lub edytować pliki, które są większe niż pamięć?)

Oczywiście morelub lesssą dobrym podejściem do zwykłego czytania plików - lessnawet oferują vitakie skróty klawiszowe do przewijania i wyszukiwania.

Freshmeat szukaj w „dużych plików” sugeruje, że dwie redaktorzy będą szczególnie dostosowane do Twoich potrzeb.

Jednym z nich byłby: lfhex ... duży edytor szesnastkowy plików (zależny od Qt). To oczywiście pociąga za sobą użycie GUI.

Inny wydaje się być odpowiedni do użycia na konsoli: hed ... i twierdzi, że ma viminterfejs podobny do a (w tymex tryb?).

Jestem pewien, że widziałem inne edytory dla systemu Linux / UNIX, które były w stanie przeglądać pliki bez ładowania ich całości do pamięci. Jednak nie pamiętam żadnego z ich nazwisk. Robię tę odpowiedź jako wpis typu "wiki", aby zachęcić innych do dodawania swoich linków do takich edytorów. (Tak, znam sposoby obejścia tego problemu za pomocą spliti cat; ale myślę o edytorach, zwłaszcza edytorach konsol / curses, które mogą się z tego obejść i zaoszczędzić nam czasu / opóźnień i narzutu miejsca na dysku, które pociągają za sobą takie podejścia) .

Jim Dennis
źródło
23

Ponieważ nie musisz faktycznie edytować pliku:

  1. view (lub vim -R ) powinien działać dość dobrze na dużych plikach.
  2. Możesz też użyć morelubless
ChssPly76
źródło
Mówiąc „dławiki” masz na myśli, że otwarcie zajmuje trochę czasu? A może faktycznie się zawiesza? Otwarcie pliku 2,7 GB na moim niezbyt nowym Linuksie zajmuje nieco ponad 4 minuty view(właśnie wypróbowane i zmierzone w czasie). To prawda, to nie jest dokładnie natychmiastowe, ale działa.
ChssPly76
Tak, to się zatrzymuje. Jestem pewien, że gdybym czekał, w końcu się otworzy. Poszedłem z mniej, ponieważ otwiera się natychmiast i jestem przyzwyczajony do nawigacji.
hoju
9

Napisałem mały skrypt na podstawie odpowiedzi Floriana, który używa nano (mój ulubiony edytor):

#!/bin/sh

if [ "$#" -ne 3 ]; then
  echo "Usage: $0 hugeFilePath startLine endLine" >&2
  exit 1
fi

sed -n -e $2','$3'p' -e $3'q' $1 > hfnano_temporary_file
nano hfnano_temporary_file
(head -n `expr $2 - 1` $1; cat hfnano_temporary_file; sed -e '1,'$3'd' $1) > hfnano_temporary_file2
cat hfnano_temporary_file2 > $1
rm hfnano_temporary_file hfnano_temporary_file2

Użyj tego w ten sposób:

sh hfnano yourHugeFile 3 8

W tym przykładzie nano otworzy linie od 3 do 8, możesz je edytować, a kiedy zapiszesz i wyjdziesz, te linie w ogromnym pliku zostaną automatycznie nadpisane twoimi zapisanymi liniami.

BT
źródło
3

Miałem ten sam problem, ale był to zrzut mysql o pojemności 300 GB i chciałem się go pozbyć DROPi zmienić CREATE TABLEna, CREATE TABLE IF NOT EXISTSwięc nie chciałem uruchamiać dwóch wywołań sed. Napisałem ten szybki skrypt Ruby, aby oszukać plik z tymi zmianami:

#!/usr/bin/env ruby

matchers={
    %q/^CREATE TABLE `foo`/ => %q/CREATE TABLE IF NOT EXISTS `foo`/,
    %q/^DROP TABLE IF EXISTS `foo`;.*$/ => "-- DROP TABLE IF EXISTS `foo`;"
}

matchers.each_pair { |m,r|
    STDERR.puts "%s: %s" % [ m, r ]
}

STDIN.each { |line|
    #STDERR.puts "line=#{line}"
    line.chomp!
    unless matchers.length == 0
        matchers.each_pair { |m,r|
            re=/#{m}/
            next if line[re].nil?
            line.sub!(re,r)
            STDERR.puts "Matched: #{m} -> #{r}"
            matchers.delete(m)
            break
        }
    end
    puts line
}

Wywołane jak

./mreplace.rb < foo.sql > foo_two.sql
Steeve McCauley
źródło
Pamiętaj tylko o uruchomieniu, aby uruchomić go jako exe chmod +x mreplace.rb, możesz też po prosturuby mreplace.rb ..
Smar
Dzięki @Steeve McCauley! Dobra robota. Dokładnie tego szukałem szukając odpowiedzi na to pytanie.
Nate Ritter,
3

W przypadku dużych jednowierszowych (drukuje znaki od 1do 99):

cut -c 1-99 filename
DmitrySandalov
źródło
2

Jest już późno, ale jeśli chcesz po prostu nawigować po pliku bez jego edycji, catmożesz też wykonać to zadanie.

% cat filename | less

lub alternatywnie proste:

% less filename
chepukha
źródło
8
Zwróć uwagę, że cattingowanie pliku w pierwszej kolejności jest szalenie głupie, ponieważ oznacza to, że plik byłby w całości w pamięci (więc lessmożna przeszukać plik) lub nie można go w ogóle znaleźć; catpo prostu daje statyczny strumień wyjściowy.
Smar
1

emacs działa bardzo dobrze z plikami do 100 megabajtów, użyłem go na plikach dziennika bez większych problemów.

Ale generalnie, kiedy mam jakieś zadanie analityczne, uważam, że napisanie skryptu w Perlu jest lepszym wyborem.

Andy Ross
źródło
0

Stara nić. Niemniej jednak (kalambur :)).

 $less filename

less działa wydajnie, jeśli nie chcesz edytować i po prostu się rozejrzyj, co ma miejsce w przypadku sprawdzania dużych plików dziennika.

Szukaj w less działa jak vi

Najlepsze jest to, że jest domyślnie dostępny w większości dystrybucji. Więc nie będzie problemu również dla środowiska produkcyjnego.

głębokie nurkowanie
źródło
Wyszukiwanie w pliku tekstowym 650MB z mniejszym okazał się być PITA. Używanie vim z LargeFile działa jak urok.
MariusCC
2
@MariusCC Więc nie pracowałeś z więcej niż 2 GB plików, Twój urok zniknie z awarią!
nurkowanie głębokie
-15

to jest stare, ale użyj nano, vim lub gvim

shiroxx
źródło
5
Te narzędzia nie rozwiązują problemu.
Doug Wolfgram
1
nano wypełnia pamięć i umiera na mnie.
Trynkiewicz Mariusz