1 |
gpertea |
16 |
#ifndef LayoutParser_H |
2 |
|
|
#define LayoutParser_H |
3 |
|
|
|
4 |
|
|
#include "GBase.h" |
5 |
|
|
#include "GList.hh" |
6 |
|
|
#include "GHash.hh" |
7 |
|
|
#include <stdio.h> |
8 |
|
|
//hash data associated with a contig/sequence name |
9 |
|
|
//a contig name key is always stored as its name plus .<length> |
10 |
|
|
|
11 |
|
|
class LytCtgData; |
12 |
|
|
|
13 |
|
|
struct LytSeqInterSeg { |
14 |
|
|
int segEnd, segRClip; |
15 |
|
|
int nextStart, nextLClip; |
16 |
|
|
char segRSplice, nextLSplice; |
17 |
|
|
int nextSegSeq; |
18 |
|
|
LytSeqInterSeg(int end, int nextstart, int rclip=0, int nextlclip=0, |
19 |
|
|
char segrsplice=0, char nextlsplice=0, int seqpos=0) { |
20 |
|
|
segEnd=end; segRClip=rclip; |
21 |
|
|
nextStart=nextstart; nextLClip=nextlclip; |
22 |
|
|
segRSplice=segrsplice; |
23 |
|
|
nextLSplice=nextlsplice; |
24 |
|
|
nextSegSeq=seqpos; |
25 |
|
|
} |
26 |
|
|
int length() { |
27 |
|
|
return (nextStart-segEnd-1); |
28 |
|
|
} |
29 |
|
|
}; |
30 |
|
|
|
31 |
|
|
class LytSeqInfo { //info for a sequence within the file |
32 |
|
|
int xlen; //total sequence length (with all the added * within contig) |
33 |
|
|
int interseglen; |
34 |
|
|
public: |
35 |
|
|
char *name; |
36 |
|
|
LytCtgData* contig; //contig data containing this sequence, as above |
37 |
|
|
bool segmented; |
38 |
|
|
int numisegs; // number of intersegs[] |
39 |
|
|
LytSeqInterSeg* intersegs; |
40 |
|
|
off_t fpos; //file position for the sequence data |
41 |
|
|
unsigned char reversed; |
42 |
|
|
int offs; //offset in contig (of the very left end) |
43 |
|
|
int left,right; //clear range (relative to sequence itself, max 1..xlen) |
44 |
|
|
LytSeqInfo(char* seqid, LytCtgData* ctg, int pos=0, unsigned char minus=0, |
45 |
|
|
int slen=0, int clpL=0, int clpR=0) { |
46 |
|
|
contig=ctg; |
47 |
|
|
offs=pos; |
48 |
|
|
reversed=minus; |
49 |
|
|
fpos=0; |
50 |
|
|
interseglen=0; |
51 |
|
|
xlen=slen; |
52 |
|
|
left=clpL+1; //1 if no clpL given |
53 |
|
|
right=xlen-clpR; //0 if no len given |
54 |
|
|
segmented=false; |
55 |
|
|
numisegs=0; |
56 |
|
|
name=Gstrdup(seqid); |
57 |
|
|
intersegs=NULL; |
58 |
|
|
} |
59 |
|
|
~LytSeqInfo() { |
60 |
|
|
GFREE(name); |
61 |
|
|
GFREE(intersegs); |
62 |
|
|
} |
63 |
|
|
bool hasIntrons() { return (numisegs>0); } |
64 |
|
|
void addInterSeg(int end, int nextstart, int rclip=0, int nextlclip=0, |
65 |
|
|
char splice=0, char nextsplice=0, int seqofs=0) { |
66 |
|
|
GREALLOC(intersegs,(numisegs+1)*sizeof(LytSeqInterSeg)); |
67 |
|
|
interseglen+=nextstart-end-1; |
68 |
|
|
intersegs[numisegs].segEnd=end; intersegs[numisegs].segRClip=rclip; |
69 |
|
|
intersegs[numisegs].nextStart=nextstart; intersegs[numisegs].nextLClip=nextlclip; |
70 |
|
|
intersegs[numisegs].segRSplice=splice; |
71 |
|
|
intersegs[numisegs].nextLSplice=nextsplice; |
72 |
|
|
intersegs[numisegs].nextSegSeq=seqofs; |
73 |
|
|
numisegs++; |
74 |
|
|
} |
75 |
|
|
|
76 |
|
|
void setLength(int len) { |
77 |
|
|
//should only be called BEFORE setting the real clipping coordinates |
78 |
|
|
//(left,right) |
79 |
|
|
xlen=len; |
80 |
|
|
left=1; |
81 |
|
|
right=xlen; |
82 |
|
|
} |
83 |
|
|
int length() { return xlen; } //xtended span, including introns |
84 |
|
|
int seglen() { return xlen-interseglen; } //segments only, no introns |
85 |
|
|
bool operator==(const LytSeqInfo& s) { |
86 |
|
|
return (offs+left-1==s.offs+s.left-1); |
87 |
|
|
} |
88 |
|
|
bool operator<(const LytSeqInfo& s) { |
89 |
|
|
return (offs+left-1<s.offs+s.left-1); |
90 |
|
|
} |
91 |
|
|
char* expandGaps(char* s); |
92 |
|
|
}; |
93 |
|
|
|
94 |
|
|
|
95 |
|
|
class LytCtgData { |
96 |
|
|
public: |
97 |
|
|
char* name; //contig name, as stored in file |
98 |
|
|
unsigned int len; //contig length (lsequence, from ACE file) |
99 |
|
|
int lpos, rpos; |
100 |
|
|
int numseqs; |
101 |
|
|
int offs; //some other type of user data that might be of use |
102 |
|
|
off_t fpos; //position in file for this contig's entry |
103 |
|
|
GList<LytSeqInfo> seqs; |
104 |
|
|
LytCtgData(off_t pos=0):seqs(false,false,false) { |
105 |
|
|
name=NULL; |
106 |
|
|
offs=0; |
107 |
|
|
len=0; |
108 |
|
|
numseqs=0; |
109 |
|
|
fpos=pos; |
110 |
|
|
} |
111 |
|
|
~LytCtgData() { |
112 |
|
|
GFREE(name); |
113 |
|
|
seqs.Clear(); |
114 |
|
|
} |
115 |
|
|
|
116 |
|
|
char* readName(char* s, GHash<int>& names); |
117 |
|
|
|
118 |
|
|
bool operator==(const LytCtgData& s) { |
119 |
|
|
return (strcmp(name,s.name)==0); |
120 |
|
|
} |
121 |
|
|
bool operator<(const LytCtgData& s) { |
122 |
|
|
return (strcmp(name,s.name)<0); |
123 |
|
|
} |
124 |
|
|
}; |
125 |
|
|
//callback -- called after a read or contig sequence is loaded |
126 |
|
|
typedef bool fnLytSeq(int ctgno, LytCtgData* d, LytSeqInfo* s, char* seq); |
127 |
|
|
|
128 |
|
|
class LayoutParser { |
129 |
|
|
protected: |
130 |
|
|
FILE* f; //file stream |
131 |
|
|
off_t f_pos; |
132 |
|
|
char* fname; |
133 |
|
|
LytCtgData* currentContig; // currently loaded contig -- for browsing/loading |
134 |
|
|
int numContigs; //total number of contigs found in this file |
135 |
|
|
//int numSeqs; //total number of (distinct) sequences found in this file |
136 |
|
|
GHash<LytSeqInfo> seqinfo; //sequence locations in the file |
137 |
|
|
GHash<int> ctgIDs; //contig IDs, to make them unique! |
138 |
|
|
|
139 |
|
|
GList<LytCtgData> contigs; //list of contig names with their size, |
140 |
|
|
//number of sequences and filepos |
141 |
|
|
protected: |
142 |
|
|
GLineReader* linebuf; //the line buffer |
143 |
|
|
off_t fskipTo(const char* linestart, const char* butnot=NULL); |
144 |
|
|
bool startsWith(const char* s, const char* start, int tlen); |
145 |
|
|
virtual LytSeqInfo* addSeq(char* s, LytCtgData* ctg); |
146 |
|
|
int seek(off_t offset) { |
147 |
|
|
int r=fseeko(f, offset, SEEK_SET); |
148 |
|
|
if (r==0) f_pos=offset; |
149 |
|
|
return r; |
150 |
|
|
} |
151 |
|
|
|
152 |
|
|
public: |
153 |
|
|
LayoutParser(const char* filename):contigs(false,true) { |
154 |
|
|
f=NULL; |
155 |
|
|
f_pos=0; |
156 |
|
|
numContigs=0; |
157 |
|
|
currentContig=NULL; |
158 |
|
|
if (filename==NULL) { |
159 |
|
|
f=stdin; |
160 |
|
|
fname=Gstrdup("stdin"); |
161 |
|
|
} |
162 |
|
|
else |
163 |
|
|
fname=Gstrdup(filename); |
164 |
|
|
linebuf=new GLineReader(); |
165 |
|
|
} |
166 |
|
|
virtual ~LayoutParser() { |
167 |
|
|
ctgIDs.Clear(); |
168 |
|
|
GFREE(fname); |
169 |
|
|
delete linebuf; |
170 |
|
|
close(); |
171 |
|
|
numContigs=0; |
172 |
|
|
seqinfo.Clear(); |
173 |
|
|
contigs.Clear(); |
174 |
|
|
} |
175 |
|
|
virtual bool open(); |
176 |
|
|
void close(); |
177 |
|
|
virtual bool parse(fnLytSeq* seqfn=NULL); //load all the file offsets |
178 |
|
|
virtual bool parseContigs(); //load all the file offsets for contigs |
179 |
|
|
virtual bool loadContig(int ctgidx, fnLytSeq* seqfn=NULL, bool re_pos=true); //for loading by browsing |
180 |
|
|
//if parsefn is not NULL, it is executed, passing the sequence data(first time, with the contig sequence) |
181 |
|
|
//if parserfn returns true, the data is freed after it is processed |
182 |
|
|
virtual char getFileType() { return 'L'; } |
183 |
|
|
//sequence loading - only by request |
184 |
|
|
LytCtgData* getContig(int idx) { return contigs[idx]; } |
185 |
|
|
virtual char* getSeq(LytSeqInfo* sqinfo) { return NULL; } |
186 |
|
|
virtual char* getContigSeq(LytCtgData* ctgdata) { return NULL; } |
187 |
|
|
int getNumContigs() { return numContigs; } |
188 |
|
|
//int getNumSeqs() { return numSeqs; } |
189 |
|
|
off_t getFilePos() { return f_pos; } |
190 |
|
|
//sorting the list of contigs: |
191 |
|
|
void contigsByName(); |
192 |
|
|
void contigsByLen(); |
193 |
|
|
void contigsByNumSeqs(); |
194 |
|
|
}; |
195 |
|
|
|
196 |
|
|
#endif |