打开ofstream作为类属性

时间:2018-05-06 18:52:15

标签: c++ object fstream

我想添加一个open ofstream作为类(Barcode)属性。目标是在main()中实现几个条形码,每个条形码都能写入特定文件。此外,我决定将所有条形码存储在一个属于Barcodes类的向量中,尽管它可能没用。

这是我的代码:

#include <iostream>
#include <fstream>
#include <string>
#include <vector>
#include <sys/stat.h>

using namespace std;

class Barcode {
    public:
        // Constructor
        Barcode(string bcName, string bcSeq, string end, string const & fileName): 
            m_bcName(bcName), m_bcSeq(bcSeq), m_end(end), m_ofStream(fileName.c_str(), ios::app) {}

        // Getters
        string getBCName() const {
            return m_bcName;
        }        
        string getBCSeq() const {
            return m_bcSeq;
        }

        //setter
        void reportRead(string toReport) {
            m_ofStream << toReport;
        }

    private:
        string m_bcName;
        string m_bcSeq;
        string m_end;
        ofstream m_ofStream;
};


class Barcodes {
    public:
        // Constructor
        Barcodes(string barcodesFile, string end): m_barcodesFile(barcodesFile), m_end(end) {
            initializeBarcodes();  
        }

        // Getters
        vector<Barcode> getBCs() {
            return m_barcodes;
        }

        // Other
        void initializeBarcodes() {
            ifstream flow(m_barcodesFile);
            if(!flow) {
                cerr << "ERROR: Could'n find the \"barcode.txt\" file." << endl;
            }

            else {
                string line, name, seq;
                // parse each line of the barcode file
                while(getline(flow, line)) {
                    //get the name and sequence of the barcodes
                    name = line.substr(0, 4);
                    seq = line.substr(5, 6);

                    //create the corresponding Barcode
                    string fileName = "Demultiplexed_Reads/" + name + "." + m_end + ".fastq";
                    Barcode bc(name, seq, m_end, fileName);
                    //add them in the corresponding vector
                    m_barcodes.push_back(bc);
                }
            }
        }

    private:
        string m_barcodesFile;
        string m_end;
        vector<Barcode> m_barcodes;
};

int main(int argc, char* argv[]) {

    //Create a new "Demultiplexed_Reads" folder
    system("rm -rf Demultiplexed_Reads");
    if(mkdir("Demultiplexed_Reads", 0755) != 0) {
        cerr << "ERROR: Couldn't create the Demultiplexed folder." << endl;
        return 1;
    }

    else {

        // Get the files to demultiplex
        string f1 = argv[1];
        string f2 = argv[2];

        // Generate the vectors of barcodes
        Barcodes bcs1("barcodes.txt", "end1");
        vector<Barcode> barcodes1(bcs1.getBCs());
        Barcodes bcs2("barcodes.txt", "end2");
        vector<Barcode> barcodes2(bcs2.getBCs());

        // Demultiplex the reads of the end1
        Demultiplexer dm1(f1, barcodes1, "end1");
        dm1.demultiplex();
        cout << "Reads of end1 demultiplexed" << endl;

        // Demultiplex the reads of the end2
        Demultiplexer dm2(f2, barcodes2, "end2");
        dm2.demultiplex();
        cout << "Reads of end2 demultiplexed" << endl;    

        return 0;
    }
}

但是,当我尝试编译g++ --std=c++11 myProg.cpp -o myProg时,我遇到了一些我不了解删除方法的错误:

In file included from /usr/include/x86_64-linux-gnu/c++/5/bits/c++allocator.h:33:0,
                 from /usr/include/c++/5/bits/allocator.h:46,
                 from /usr/include/c++/5/string:41,
                 from /usr/include/c++/5/bits/locale_classes.h:40,
                 from /usr/include/c++/5/bits/ios_base.h:41,
                 from /usr/include/c++/5/ios:42,
                 from /usr/include/c++/5/ostream:38,
                 from /usr/include/c++/5/iostream:39,
                 from Demultiplex.cpp:1:
/usr/include/c++/5/ext/new_allocator.h: In instantiation of ‘void __gnu_cxx::new_allocator<_Tp>::construct(_Up*, _Args&& ...) [with _Up = Barcode; _Args = {const Barcode&}; _Tp = Barcode]’:
/usr/include/c++/5/bits/alloc_traits.h:530:4:   required from ‘static void std::allocator_traits<std::allocator<_CharT> >::construct(std::allocator_traits<std::allocator<_CharT> >::allocator_type&, _Up*, _Args&& ...) [with _Up = Barcode; _Args = {const Barcode&}; _Tp = Barcode; std::allocator_traits<std::allocator<_CharT> >::allocator_type = std::allocator<Barcode>]’
/usr/include/c++/5/bits/stl_vector.h:917:30:   required from ‘void std::vector<_Tp, _Alloc>::push_back(const value_type&) [with _Tp = Barcode; _Alloc = std::allocator<Barcode>; std::vector<_Tp, _Alloc>::value_type = Barcode]’
Demultiplex.cpp:85:44:   required from here
/usr/include/c++/5/ext/new_allocator.h:120:4: error: use of deleted function ‘Barcode::Barcode(const Barcode&)’
  { ::new((void *)__p) _Up(std::forward<_Args>(__args)...); }
    ^
Demultiplex.cpp:18:7: note: ‘Barcode::Barcode(const Barcode&)’ is implicitly deleted because the default definition would be ill-formed:
 class Barcode {
       ^
Demultiplex.cpp:18:7: error: use of deleted function ‘std::basic_ofstream<_CharT, _Traits>::basic_ofstream(const std::basic_ofstream<_CharT, _Traits>&) [with _CharT = char; _Traits = std::char_traits<char>]’
In file included from Demultiplex.cpp:2:0:
/usr/include/c++/5/fstream:723:7: note: declared here
       basic_ofstream(const basic_ofstream&) = delete;
       ^
In file included from /usr/include/c++/5/vector:62:0,
                 from Demultiplex.cpp:4:
/usr/include/c++/5/bits/stl_construct.h: In instantiation of ‘void std::_Construct(_T1*, _Args&& ...) [with _T1 = Barcode; _Args = {const Barcode&}]’:
/usr/include/c++/5/bits/stl_uninitialized.h:75:18:   required from ‘static _ForwardIterator std::__uninitialized_copy<_TrivialValueTypes>::__uninit_copy(_InputIterator, _InputIterator, _ForwardIterator) [with _InputIterator = __gnu_cxx::__normal_iterator<const Barcode*, std::vector<Barcode> >; _ForwardIterator = Barcode*; bool _TrivialValueTypes = false]’
/usr/include/c++/5/bits/stl_uninitialized.h:126:15:   required from ‘_ForwardIterator std::uninitialized_copy(_InputIterator, _InputIterator, _ForwardIterator) [with _InputIterator = __gnu_cxx::__normal_iterator<const Barcode*, std::vector<Barcode> >; _ForwardIterator = Barcode*]’
/usr/include/c++/5/bits/stl_uninitialized.h:281:37:   required from ‘_ForwardIterator std::__uninitialized_copy_a(_InputIterator, _InputIterator, _ForwardIterator, std::allocator<_Tp>&) [with _InputIterator = __gnu_cxx::__normal_iterator<const Barcode*, std::vector<Barcode> >; _ForwardIterator = Barcode*; _Tp = Barcode]’
/usr/include/c++/5/bits/stl_vector.h:322:31:   required from ‘std::vector<_Tp, _Alloc>::vector(const std::vector<_Tp, _Alloc>&) [with _Tp = Barcode; _Alloc = std::allocator<Barcode>]’
Demultiplex.cpp:63:20:   required from here
/usr/include/c++/5/bits/stl_construct.h:75:7: error: use of deleted function ‘Barcode::Barcode(const Barcode&)’
     { ::new(static_cast<void*>(__p)) _T1(std::forward<_Args>(__args)...); }

有人知道问题是什么吗?

非常感谢你!

1 个答案:

答案 0 :(得分:0)

所以我找到了解决问题的方法,所以我只想写下我在这里使用的解决方案,以防对某人有用。

最后,我在方法中创建了一个ofstreams向量,它写入输出文件而不是将流放入对象中。我在读取ans输入文件中的行的循环之前就完成了它。

正如你所说,诀窍是不要尝试复制流,因为它是不可能的。但是他们的参考可以移动到矢量中。所以我使用了move函数,它是自C ++ 11以来的标准:

ofstream ofs(fileName);
ofStreams.push_back(move(ofs));

我为我工作并允许我的程序比打开一个流更快,并为我需要排序的每一行关闭它。