]> git.donarmstrong.com Git - rsem.git/blob - ReadReader.h
Fixed a bug in perl scripts for printing error messages
[rsem.git] / ReadReader.h
1 #ifndef READREADER_H_
2 #define READREADER_H_
3
4 #include<cstdio>
5 #include<cstring>
6 #include<cstdlib>
7 #include<iostream>
8 #include<cassert>
9 #include<fstream>
10
11 #include "utils.h"
12 #include "SingleRead.h"
13 #include "SingleReadQ.h"
14 #include "PairedEndRead.h"
15 #include "PairedEndReadQ.h"
16 #include "ReadIndex.h"
17
18
19 template<class ReadType>
20 class ReadReader {
21 public:
22         ReadReader() { s = 0; indices = NULL; arr = NULL; hasPolyA = false; seedLen = -1; }
23         ReadReader(int s, char readFs[][STRLEN], bool hasPolyA = false, int seedLen = -1);
24         ~ReadReader();
25
26         void setIndices(ReadIndex** indices) {
27                 this->indices = indices;
28         }
29
30         bool locate(READ_INT_TYPE); // You should guarantee that indices exist and rid is valid, otherwise return false; If it fails, you should reset it manually!
31         void reset();
32
33         bool next(ReadType& read, int flags = 7) {
34                 bool success = read.read(s, (std::istream**)arr, flags);
35                 if (success && seedLen > 0) { read.calc_lq(hasPolyA, seedLen); }
36                 return success;
37         }
38
39 private:
40         int s; // number of files
41         ReadIndex **indices;
42         std::ifstream** arr;
43         std::streampos *locations;
44
45         bool hasPolyA;
46         int seedLen;
47 };
48
49 template<class ReadType>
50 ReadReader<ReadType>::ReadReader(int s, char readFs[][STRLEN], bool hasPolyA, int seedLen) {
51         assert(s > 0);
52         this->s = s;
53         arr = new std::ifstream*[s];
54         locations = new std::streampos[s];
55         indices = NULL;
56         for (int i = 0; i < s; i++) {
57                 arr[i] = new std::ifstream(readFs[i]);
58                 if (!arr[i]->is_open()) { fprintf(stderr, "Cannot open %s! It may not exist.\n", readFs[i]); exit(-1); }
59                 locations[i] = arr[i]->tellg();
60         }
61         this->hasPolyA = hasPolyA;
62         this->seedLen = seedLen;
63 }
64
65 template<class ReadType>
66 ReadReader<ReadType>::~ReadReader() {
67         indices = NULL;
68         if (arr != NULL) {
69                 for (int i = 0; i < s; i++) {
70                         arr[i]->close();
71                         delete arr[i];
72                 }
73                 delete[] arr;
74         }
75         if (locations != NULL) {
76                 delete[] locations;
77         }
78 }
79
80 template<class ReadType>
81 bool ReadReader<ReadType>::locate(READ_INT_TYPE rid) {
82         READ_INT_TYPE crid = -1;
83         ReadType read;
84
85         if (indices == NULL) return false;
86
87         //We should make sure that crid returned by each indices is the same
88         for (int i = 0; i < s; i++) {
89                 READ_INT_TYPE val = indices[i]->locate(rid, *arr[i]);
90                 if (i == 0) { crid = val; } else { assert(crid == val); }
91         }
92         assert(crid <= rid);
93         while (crid < rid && read.read(s, (std::istream**)arr, 0)) ++crid;
94
95         if (crid < rid) return false;
96
97         std::streampos tmp[s];
98         for (int i = 0; i < s; i++) { tmp[i] = arr[i]->tellg(); }
99
100         if (!read.read(s, (std::istream**)arr, 0)) return false;
101
102         for (int i = 0; i < s; i++) {
103                 locations[i] = tmp[i];
104                 arr[i]->seekg(locations[i]);
105         }
106
107         return true;
108 }
109
110 template<class ReadType>
111 void ReadReader<ReadType>::reset() {
112         for (int i = 0; i < s; i++) {
113                 arr[i]->seekg(locations[i]);
114         }
115 }
116
117 #endif /* READREADER_H_ */