不读第一行

时间:2015-03-13 20:24:14

标签: c++ file vector getline

我使用以下代码将文件(b.txt)中的信息读入矢量。 每次执行时,程序都会从​​第二行开始读取。 所以vector_b [0] =第二行而不是第一行。

我还不习惯c ++ 希望你能帮忙

string line_b;
int idx = -1;
float *vector_b = new float[1];
float element_b;
if (file_b.is_open() && file_b.good()) {
    cout << "File is open. \n";
    while (getline(file_b, line_b)) {
        stringstream stream_b(line_b);
        while(1) {
            stream_b >> element_b;
            if(!stream_b) {
                break; }
            idx = idx+1;
            float *tempArr = new float [idx];
            copy(vector_b, vector_b + idx, tempArr);
            tempArr[idx] = element_b;
            delete [] vector_b;
            vector_b = tempArr;
        }
    }        
    } 
    else {
        cout << "Failed to open file.";
    }

1 个答案:

答案 0 :(得分:0)

您可以尝试以下内容。您可以尝试vector而不是动态数组。他们更灵活,在大多数情况下更快。你不必担心在释放,双重释放或内存泄漏后使用......所以是的......矢量规则......

int main() {
    std::ifstream file_b;
    file_b.open("Some-file.cpp");

    std::string line_b;
    // vector_b is a vector of doubles
    std::vector<double> vector_b();
    double element_b;
    if (file_b.is_open() && file_b.good()) {
        std::cout << "File is open. \n" << std::endl;
        while(getline(file_b, line_b)) {
            std::stringstream stream_b(line_b);
            // You don't need a second if.
            while(stream_b) {
                stream_b >> element_b;
                // append element_b to your vector
                vector_b.push_back(element_b);
            }
        }
    } else {
        std::cout << "Failed to open file." << std::endl;
    }
}

但是,如果您不能使用向量,我建议您考虑创建一个容器类,如下面列出的类和用法。我不相信自己要记住释放记忆,所以有时候最好建立一个班级。我在valgrind下几次测试了下面的类,所以不应该有任何泄漏,但没有承诺。我非常匆忙。

#include <cassert>

// use a templated class so we can use it with different types
template<typename T>
class Container {
    private:
        unsigned int m_size;
        unsigned int m_capacity;
        T* m_array;

    public:
        // Any time you make a container class make sure you follow the
        // rule of 5 with C++11 or the rule of 3 for prior compilers
        // 1) Copy Constructor
        // 2) Move Constructor (C++11)
        // 3) Copy Assignment Operator
        // 4) Move Assignment Operator (C++11)
        // 5) Destructor

        // Default constructor
        Container() { }

        // Constructor we'll use
        Container(unsigned sz) :
            m_size(0),
            m_capacity(sz),
            m_array(new T[sz]) { }

        // Copy constructor
        Container(const Container& src) :
            m_size(src.m_size),
            m_capacity(src.m_size),
            m_array(new T[src.m_size]) {
                for(unsigned i = 0; i < m_size; ++i) {
                    // copy values
                    m_array[i] = src.m_array[i];
                }
            }

        // Move constructor
        Container(Container&& src) {
            // "steal" the sources members
            m_capacity = src.m_capacity;
            m_size = src.m_size;
            m_array = src.m_array;
            // "destroy" the sources members
            src.m_size = 0;
            src.m_capacity = 0;
            src.m_array = nullptr;
        }

        // Destructor
        ~Container() {
            delete[] m_array;
        }

        // Copy assignment operator
        Container& operator=(const Container& src) {
            // check to make sure you're copying a different source
            if(this == &src) {
                return *this;
            }
            // free your current memory
            delete[] m_array;
            // make a new array and copy the sources values
            m_array = new T[src.m_size];
            for(unsigned i = 0; i < src.m_size; ++i) {
                m_array[i] = src.m_array[i];
            }
            // copy the size parameters
            m_size = src.m_size;
            m_capacity = src.m_capacity;
            return(*this);
        }

        // Move assignment operator
        Container& operator=(Container&& src) {
            // check to make sure you're copying a different source
            if(this == &src) {
                return *this;
            }
            // free your current memory
            delete[] m_array;
            // "steal" the sources members
            m_array = src.m_array;
            m_size = src.m_size;
            m_capacity = src.m_capacity;
            // "destroy" the sources members
            src.m_array = nullptr;
            src.m_size = 0;
            src.m_capacity = 0;
            return(*this);
        }

        void resize(unsigned int sz) {
            // make sure you're not shrinking the container
            if(sz > m_capacity) {
                // make a temporary array
                T* tmp = new T[sz];
                for(unsigned i = 0; i < m_size; ++i) {
                    // copy the values to the temporary array
                    tmp[i] = m_array[i];
                }
                // free your current memory
                delete[] m_array;
                // "steal" the temporary array
                m_array = tmp;
                // release tmp's handle on the memory
                tmp = nullptr;
                // inform your object that it has more memory now
                m_capacity = sz;
            }
        }

        void push_back(const T& src) {
            // check if you have enough space to append a value
            if(m_size + 1 > m_capacity) {
                // if not, double your current size, so you don't have
                // to do it every time
                resize((m_capacity + 1) * 2);
            }
            // increment the size member and append the value to your array
            m_array[m_size++] = src;
        }

        T& operator[](unsigned index) {
            // make sure the index value is in-bounds
            assert(index < m_size);
            return(m_array[index]);
        }

        size_t size() { return(m_size); }
};

用法:

int main(int argc, char *argv[]) {
    Container<std::string> vector_b(1);
    std::ifstream file_b;
    file_b.open("Sleep.cpp");

    std::string line_b;
    std::string element_b;
    if (file_b.is_open() && file_b.good()) {
        std::cout << "File is open. \n" << std::endl;
        while(getline(file_b, line_b)) {
            std::stringstream stream_b(line_b);
                while(stream_b) {
                    stream_b >> element_b;
                    vector_b.push_back(element_b);
                }
        }
    } else {
        std::cout << "Failed to open file." << std::endl;;
    }

    for(unsigned i = 0; i < vector_b.size(); ++i) {
        std::cout << vector_b[i] << std::endl;
    }
}

正如您所看到的,使用动态内存分配是一件痛苦的事情,通常应该避免,或者至少要小心谨慎地处理它们。