打印出文件的最后10行

问题描述:

我想要打印出文本文件的最后10行。与此程序我已经能够读取整个文本文件,但我不知道如何处理文本文件保存的数组,如何帮助?打印出文件的最后10行

// Textfile output 
#include<fstream> 
#include<iostream> 
#include<iomanip> 
using namespace std; 

int main() { 
    int i=1; 
    char zeile[250], file[50]; 
    cout << "filename:" << flush; 
    cin.get(file,50);       ///// (1) 
    ifstream eingabe(datei , ios::in);   /////(2) 
    if (eingabe.good()) {      /////(3)   
     eingabe.seekg(0L,ios::end);    ////(4) 
     cout << "file:"<< file << "\t" 
      << eingabe.tellg() << " Bytes"  ////(5) 
      << endl; 
     for (int j=0; j<80;j++) 
      cout << "_"; 
      cout << endl; 
     eingabe.seekg(0L, ios::beg);    ////(6) 
     while (!eingabe.eof()){     ///(7) 
      eingabe.getline(zeile,250);   ///(8) 
      cout << setw(2) << i++ 
        << ":" << zeile << endl; 
      }  
      } 
    else 
     cout <<"dateifehler oder Datei nicht gefunden!" 
      << endl; 

      return 0; 
    } 
+3

虽然你可能已经知道这一点,UNIX [尾巴](http://en.wikipedia.org/wiki/Tail_(UNIX))命令究竟是干什么的你要。 – darioo 2011-04-26 18:45:45

+0

@darioo:这个问题听起来像作业。 – 2011-04-26 18:57:33

+3

顺便说一句,如果你寻找文件的末尾,然后向后寻找你的起点,而不是解析整个文件,你会发现它在更大的文件上快得多**。 – 2011-04-26 18:59:58

做一个圆形缓冲器用10个槽和在读取文件中的行,将它们放入该缓冲器中。当你完成thr文件时,做一个位置++去第一个元素并将它们全部打印出来。 如果文件少于10行,请留意空值。

  1. 有一个字符串与大小的数组10
  2. 阅读的第一行,并存入数组
  3. 继续阅读,直到数组已满
  4. 一旦数组已满删除第一项,以便您可以输入新行 重复步骤3和4,直到文件读完。

基本上,您并未将文件内容保存到任何阵列。下面的示例会给你一个良好的开端:

#include <iostream> 
#include <vector> 
#include <string> 

int main (int, char **) 
{ 
    // Ask user for path to file. 
    std::string path; 
    std::cout << "filename:"; 
    std::getline(std::cin, path); 

    // Open selected file.  
    std::ifstream file(path.c_str()); 
    if (!file.is_open()) 
    { 
     std::cerr << "Failed to open '" << path << "'." << std::endl; 
     return EXIT_FAILURE; 
    } 

    // Read lines (note: stores all of it in memory, might not be your best option). 
    std::vector<std::string> lines; 
    for (std::string line; std::getline(file,line);) 
    { 
     lines.push_back(line); 
    } 

    // Print out (up to) last ten lines. 
    for (std::size_t i = std::min(lines.size(), std::size_t(10)); i < lines.size(); ++i) 
    { 
     std::cout << lines[i] << std::endl; 
    } 
} 

它可能是明智的,避免存储整个文件到内存中,这样你就可以重新写最后2段是这样的:

// Read up to 10 lines, accumulating. 
std::deque<std::string> lines; 
for (std::string line; lines.size() < 0 && getline(file,line);) 
{ 
    lines.push_back(line); 
} 

// Read the rest of the file, adding one, dumping one. 
for (std::string line; getline(file,line);) 
{ 
    lines.pop_front(); 
    lines.push_back(line); 
} 

// Print out whatever is left (up to 10 lines). 
for (std::size_t i = 0; i < lines.size(); ++i) 
{ 
    std::cout << lines[i] << std::endl; 
} 

eof()函数不会做你和它似乎有一百万其他C++新手认为它所做的事情。它不能预测下一次阅读是否会奏效。在任何其他语言的C++中,您必须在读取之前检查每个读取操作的状态,而不是输入流的状态。所以规范的C++读取线循环是:

while (eingabe.getline(zeile,250)) { 
    // do something with zeile 
} 

此外,你应该读成std::string,并摆脱250的价值。

试试这个:

#include <list> 
#include <string> 
#include <iostream> 
#include <fstream> 
#include <algorithm> 
#include <iterator> 

//一个知道如何读取线使用运营商>>

struct Line 
{ 
    std::string theLine; 
    operator std::string const&() const { return theLine; } 
    friend std::istream& operator>>(std::istream& stream, Line& l) 
    { 
     return std::getline(stream, l.theLine); 
    } 
}; 

//循环缓冲器,仅保存最后n行类。

class Buffer 
{ 
    public: 
     Buffer(size_t lc) 
      : lineCount(lc) 
     {} 
     void push_back(std::string const& line) 
     { 
      buffer.insert(buffer.end(),line); 
      if (buffer.size() > lineCount) 
      { 
       buffer.erase(buffer.begin()); 
      } 
     } 
     typedef std::list<std::string>  Cont; 
     typedef Cont::const_iterator  const_iterator; 
     typedef Cont::const_reference  const_reference; 
     const_iterator begin() const  { return buffer.begin(); } 
     const_iterator end() const  { return buffer.end();} 

    private: 
     size_t      lineCount; 
     std::list<std::string>  buffer; 
};  

//主

int main() 
{ 
    std::ifstream file("Plop"); 
    Buffer   buffer(10); 

    // Copy the file into the special buffer. 
    std::copy(std::istream_iterator<Line>(file), std::istream_iterator<Line>(), 
      std::back_inserter(buffer)); 

    // Copy the buffer (which only has the last 10 lines) 
    // to std::cout 
    std::copy(buffer.begin(), buffer.end(), 
      std::ostream_iterator<std::string>(std::cout, "\n")); 
}