]> git.donarmstrong.com Git - mothur.git/blob - listotulabelscommand.cpp
working on pam
[mothur.git] / listotulabelscommand.cpp
1 //
2 //  listotucommand.cpp
3 //  Mothur
4 //
5 //  Created by Sarah Westcott on 5/15/12.
6 //  Copyright (c) 2012 Schloss Lab. All rights reserved.
7 //
8
9 #include "listotulabelscommand.h"
10 #include "inputdata.h"
11
12 //**********************************************************************************************************************
13 vector<string> ListOtuLabelsCommand::setParameters(){   
14         try {
15         CommandParameter pshared("shared", "InputTypes", "", "", "SharedRel", "SharedRel", "none","otulabels",false,false,true); parameters.push_back(pshared);
16                 CommandParameter prelabund("relabund", "InputTypes", "", "", "SharedRel", "SharedRel", "none","otulabels",false,false); parameters.push_back(prelabund);
17         CommandParameter plist("list", "InputTypes", "", "", "SharedRel", "SharedRel", "none","otulabels",false,false); parameters.push_back(plist);
18         CommandParameter pgroups("groups", "String", "", "", "", "", "","",false,false); parameters.push_back(pgroups);
19                 CommandParameter plabel("label", "String", "", "", "", "", "","",false,false); parameters.push_back(plabel);
20         //every command must have inputdir and outputdir.  This allows mothur users to redirect input and output files.
21                 CommandParameter pinputdir("inputdir", "String", "", "", "", "", "","",false,false); parameters.push_back(pinputdir);
22                 CommandParameter poutputdir("outputdir", "String", "", "", "", "", "","",false,false); parameters.push_back(poutputdir);
23                 
24                 vector<string> myArray;
25                 for (int i = 0; i < parameters.size(); i++) {   myArray.push_back(parameters[i].name);          }
26                 return myArray;
27         }
28         catch(exception& e) {
29                 m->errorOut(e, "ListOtuLabelsCommand", "setParameters");
30                 exit(1);
31         }
32 }
33 //**********************************************************************************************************************
34 string ListOtuLabelsCommand::getHelpString(){   
35         try {
36                 string helpString = "";
37                 helpString += "The list.otulabels lists otu labels from shared, relabund or list file. The results can be used by the get.otulabels to select specific otus with the output from classify.otu, otu.association, or corr.axes.\n";
38                 helpString += "The list.otulabels parameters are: shared, relabund, label and groups.\n";
39                 helpString += "The label parameter is used to analyze specific labels in your input.\n";
40                 helpString += "The groups parameter allows you to specify which of the groups you would like analyzed.\n";
41                 helpString += "The list.otulabels commmand should be in the following format: \n";
42                 helpString += "list.otulabels(shared=yourSharedFile, groups=yourGroup1-yourGroup2)\n";
43                 return helpString;
44         }
45         catch(exception& e) {
46                 m->errorOut(e, "ListOtuLabelsCommand", "getHelpString");
47                 exit(1);
48         }
49 }
50 //**********************************************************************************************************************
51 string ListOtuLabelsCommand::getOutputPattern(string type) {
52     try {
53         string pattern = "";
54         
55         if (type == "otulabels") {  pattern = "[filename],[distance],otulabels"; } 
56         else { m->mothurOut("[ERROR]: No definition for type " + type + " output pattern.\n"); m->control_pressed = true;  }
57         
58         return pattern;
59     }
60     catch(exception& e) {
61         m->errorOut(e, "ListOtuLabelsCommand", "getOutputPattern");
62         exit(1);
63     }
64 }
65 //**********************************************************************************************************************
66 ListOtuLabelsCommand::ListOtuLabelsCommand(){   
67         try {
68                 abort = true; calledHelp = true;
69                 setParameters();
70         vector<string> tempOutNames;
71                 outputTypes["otulabels"] = tempOutNames; 
72         }
73         catch(exception& e) {
74                 m->errorOut(e, "ListOtuLabelsCommand", "ListOtuLabelsCommand");
75                 exit(1);
76         }
77 }
78 //**********************************************************************************************************************
79 ListOtuLabelsCommand::ListOtuLabelsCommand(string option)  {
80         try {
81                 abort = false; calledHelp = false;   
82                 allLines = 1;
83         
84                 //allow user to run help
85                 if(option == "help") { help(); abort = true; calledHelp = true; }
86                 else if(option == "citation") { citation(); abort = true; calledHelp = true;}
87                 
88                 else {
89                         //valid paramters for this command
90                         vector<string> myArray = setParameters();
91                         
92                         OptionParser parser(option);
93                         map<string,string> parameters = parser.getParameters();
94                         
95                         ValidParameters validParameter;
96                         map<string,string>::iterator it;
97                         //check to make sure all parameters are valid for command
98                         for (it = parameters.begin(); it != parameters.end(); it++) { 
99                                 if (validParameter.isValidParameter(it->first, myArray, it->second) != true) {  abort = true;  }
100                         }
101                         
102                         
103                         //if the user changes the input directory command factory will send this info to us in the output parameter 
104                         string inputDir = validParameter.validFile(parameters, "inputdir", false);              
105                         if (inputDir == "not found"){   inputDir = "";          }
106                         else {
107                 
108                 //edit file types below to include only the types you added as parameters
109                 
110                                 string path;
111                 it = parameters.find("relabund");
112                                 //user has given a template file
113                                 if(it != parameters.end()){ 
114                                         path = m->hasPath(it->second);
115                                         //if the user has not given a path then, add inputdir. else leave path alone.
116                                         if (path == "") {       parameters["relabund"] = inputDir + it->second;         }
117                                 }
118                 
119                 it = parameters.find("shared");
120                                 //user has given a template file
121                                 if(it != parameters.end()){ 
122                                         path = m->hasPath(it->second);
123                                         //if the user has not given a path then, add inputdir. else leave path alone.
124                                         if (path == "") {       parameters["shared"] = inputDir + it->second;           }
125                                 }
126                 
127                 it = parameters.find("list");
128                                 //user has given a template file
129                                 if(it != parameters.end()){ 
130                                         path = m->hasPath(it->second);
131                                         //if the user has not given a path then, add inputdir. else leave path alone.
132                                         if (path == "") {       parameters["list"] = inputDir + it->second;             }
133                                 }
134             }
135             
136             vector<string> tempOutNames;
137             outputTypes["otulabels"] = tempOutNames; 
138             
139                         //check for parameters
140             sharedfile = validParameter.validFile(parameters, "shared", true);
141                         if (sharedfile == "not open") { abort = true; }
142                         else if (sharedfile == "not found") { sharedfile = ""; }
143                         else { inputFileName = sharedfile; format = "sharedfile"; m->setSharedFile(sharedfile); }
144                         
145                         relabundfile = validParameter.validFile(parameters, "relabund", true);
146                         if (relabundfile == "not open") { abort = true; }
147                         else if (relabundfile == "not found") { relabundfile = ""; }
148                         else { inputFileName = relabundfile; format = "relabund"; m->setRelAbundFile(relabundfile); }
149             
150             listfile = validParameter.validFile(parameters, "list", true);
151                         if (listfile == "not open") { abort = true; }
152                         else if (listfile == "not found") { listfile = ""; }
153                         else { inputFileName = listfile; format = "list"; m->setListFile(listfile); }
154
155             
156             if ((relabundfile == "") && (sharedfile == "") && (listfile== "")) { 
157                                 //is there are current file available for either of these?
158                                 //give priority to shared, then relabund
159                                 sharedfile = m->getSharedFile(); 
160                                 if (sharedfile != "") {  inputFileName = sharedfile; format="sharedfile"; m->mothurOut("Using " + sharedfile + " as input file for the shared parameter."); m->mothurOutEndLine(); }
161                                 else { 
162                                         relabundfile = m->getRelAbundFile(); 
163                                         if (relabundfile != "") {  inputFileName = relabundfile; format="relabund"; m->mothurOut("Using " + relabundfile + " as input file for the relabund parameter."); m->mothurOutEndLine(); }
164                                         else { 
165                         listfile = m->getListFile();
166                                                 if (listfile != "") {  inputFileName = listfile; format="list"; m->mothurOut("Using " + listfile + " as input file for the list parameter."); m->mothurOutEndLine(); }
167                         else { 
168                             m->mothurOut("No valid current files. You must provide a shared, list or relabund."); m->mothurOutEndLine(); 
169                             abort = true;
170                         }
171                                         }
172                                 }
173                         }
174             
175             //if the user changes the output directory command factory will send this info to us in the output parameter 
176                         outputDir = validParameter.validFile(parameters, "outputdir", false);           if (outputDir == "not found"){  
177                                 outputDir = m->hasPath(inputFileName); //if user entered a file with a path then preserve it    
178                         }
179             
180             string groups = validParameter.validFile(parameters, "groups", false);                      
181                         if (groups == "not found") { groups = ""; }
182                         else { m->splitAtDash(groups, Groups); }
183                         m->setGroups(Groups);
184             
185             string label = validParameter.validFile(parameters, "label", false);                        
186                         if (label == "not found") { label = ""; }
187                         else { 
188                                 if(label != "all") {  m->splitAtDash(label, labels);  allLines = 0;  }
189                                 else { allLines = 1;  }
190                         }                       
191                 }
192                 
193         }
194         catch(exception& e) {
195                 m->errorOut(e, "ListOtuLabelsCommand", "ListOtuLabelsCommand");
196                 exit(1);
197         }
198 }
199 //**********************************************************************************************************************
200
201 int ListOtuLabelsCommand::execute(){
202         try {
203                 
204                 if (abort == true) { if (calledHelp) { return 0; }  return 2;   }
205         
206         InputData input(inputFileName, format);
207         
208         if (format == "relabund") {
209             vector<SharedRAbundFloatVector*> lookup = input.getSharedRAbundFloatVectors();
210             string lastLabel = lookup[0]->getLabel();
211             
212             //if the users enters label "0.06" and there is no "0.06" in their file use the next lowest label.
213             set<string> processedLabels;
214             set<string> userLabels = labels;
215             
216             //as long as you are not at the end of the file or done wih the lines you want
217             while((lookup[0] != NULL) && ((allLines == 1) || (userLabels.size() != 0))) {
218                 
219                 if (m->control_pressed) { for (int i = 0; i < lookup.size(); i++) {  delete lookup[i];  }  for (int i = 0; i < outputNames.size(); i++) { m->mothurRemove(outputNames[i]); } return 0; }
220                 
221                 if(allLines == 1 || labels.count(lookup[0]->getLabel()) == 1){                  
222                     
223                     m->mothurOut(lookup[0]->getLabel()); m->mothurOutEndLine();
224                     
225                     createList(lookup);
226                     
227                     processedLabels.insert(lookup[0]->getLabel());
228                     userLabels.erase(lookup[0]->getLabel());
229                 }
230                 
231                 if ((m->anyLabelsToProcess(lookup[0]->getLabel(), userLabels, "") == true) && (processedLabels.count(lastLabel) != 1)) {
232                     string saveLabel = lookup[0]->getLabel();
233                     
234                     for (int i = 0; i < lookup.size(); i++) {  delete lookup[i];  }  
235                     lookup = input.getSharedRAbundFloatVectors(lastLabel);
236                     m->mothurOut(lookup[0]->getLabel()); m->mothurOutEndLine();
237                     
238                     createList(lookup);
239                     
240                     processedLabels.insert(lookup[0]->getLabel());
241                     userLabels.erase(lookup[0]->getLabel());
242                     
243                     //restore real lastlabel to save below
244                     lookup[0]->setLabel(saveLabel);
245                 }
246                 
247                 lastLabel = lookup[0]->getLabel();
248                 //prevent memory leak
249                 for (int i = 0; i < lookup.size(); i++) {  delete lookup[i]; lookup[i] = NULL; }
250                 
251                 if (m->control_pressed) { for (int i = 0; i < outputNames.size(); i++) { m->mothurRemove(outputNames[i]); }  return 0; }
252                 
253                 //get next line to process
254                 lookup = input.getSharedRAbundFloatVectors();                           
255             }
256             
257             if (m->control_pressed) {  for (int i = 0; i < outputNames.size(); i++) { m->mothurRemove(outputNames[i]); }  return 0; }
258             
259             //output error messages about any remaining user labels
260             set<string>::iterator it;
261             bool needToRun = false;
262             for (it = userLabels.begin(); it != userLabels.end(); it++) {  
263                 m->mothurOut("Your file does not include the label " + *it); 
264                 if (processedLabels.count(lastLabel) != 1) {
265                     m->mothurOut(". I will use " + lastLabel + "."); m->mothurOutEndLine();
266                     needToRun = true;
267                 }else {
268                     m->mothurOut(". Please refer to " + lastLabel + "."); m->mothurOutEndLine();
269                 }
270             }
271             
272             //run last label if you need to
273             if (needToRun == true)  {
274                 for (int i = 0; i < lookup.size(); i++) { if (lookup[i] != NULL) { delete lookup[i]; } }  
275                 lookup = input.getSharedRAbundFloatVectors(lastLabel);
276                 
277                 m->mothurOut(lookup[0]->getLabel()); m->mothurOutEndLine();
278                 
279                 createList(lookup);
280                 
281                 for (int i = 0; i < lookup.size(); i++) {  delete lookup[i];  }
282             }
283         }else if (format == "sharedfile") {
284             
285             vector<SharedRAbundVector*> lookup = input.getSharedRAbundVectors();
286             string lastLabel = lookup[0]->getLabel();
287             
288             //if the users enters label "0.06" and there is no "0.06" in their file use the next lowest label.
289             set<string> processedLabels;
290             set<string> userLabels = labels;
291             
292             //as long as you are not at the end of the file or done wih the lines you want
293             while((lookup[0] != NULL) && ((allLines == 1) || (userLabels.size() != 0))) {
294                 
295                 if (m->control_pressed) { for (int i = 0; i < lookup.size(); i++) {  delete lookup[i];  }  for (int i = 0; i < outputNames.size(); i++) { m->mothurRemove(outputNames[i]); } return 0; }
296                 
297                 if(allLines == 1 || labels.count(lookup[0]->getLabel()) == 1){                  
298                     
299                     m->mothurOut(lookup[0]->getLabel()); m->mothurOutEndLine();
300                     
301                     createList(lookup);
302                     
303                     processedLabels.insert(lookup[0]->getLabel());
304                     userLabels.erase(lookup[0]->getLabel());
305                 }
306                 
307                 if ((m->anyLabelsToProcess(lookup[0]->getLabel(), userLabels, "") == true) && (processedLabels.count(lastLabel) != 1)) {
308                     string saveLabel = lookup[0]->getLabel();
309                     
310                     for (int i = 0; i < lookup.size(); i++) {  delete lookup[i];  }  
311                     lookup = input.getSharedRAbundVectors(lastLabel);
312                     m->mothurOut(lookup[0]->getLabel()); m->mothurOutEndLine();
313                     
314                     createList(lookup);
315                     
316                     processedLabels.insert(lookup[0]->getLabel());
317                     userLabels.erase(lookup[0]->getLabel());
318                     
319                     //restore real lastlabel to save below
320                     lookup[0]->setLabel(saveLabel);
321                 }
322                 
323                 lastLabel = lookup[0]->getLabel();
324                 //prevent memory leak
325                 for (int i = 0; i < lookup.size(); i++) {  delete lookup[i]; lookup[i] = NULL; }
326                 
327                 if (m->control_pressed) { for (int i = 0; i < outputNames.size(); i++) { m->mothurRemove(outputNames[i]); }  return 0; }
328                 
329                 //get next line to process
330                 lookup = input.getSharedRAbundVectors();                                
331             }
332             
333             if (m->control_pressed) {  for (int i = 0; i < outputNames.size(); i++) { m->mothurRemove(outputNames[i]); }  return 0; }
334             
335             //output error messages about any remaining user labels
336             set<string>::iterator it;
337             bool needToRun = false;
338             for (it = userLabels.begin(); it != userLabels.end(); it++) {  
339                 m->mothurOut("Your file does not include the label " + *it); 
340                 if (processedLabels.count(lastLabel) != 1) {
341                     m->mothurOut(". I will use " + lastLabel + "."); m->mothurOutEndLine();
342                     needToRun = true;
343                 }else {
344                     m->mothurOut(". Please refer to " + lastLabel + "."); m->mothurOutEndLine();
345                 }
346             }
347             
348             //run last label if you need to
349             if (needToRun == true)  {
350                 for (int i = 0; i < lookup.size(); i++) { if (lookup[i] != NULL) { delete lookup[i]; } }  
351                 lookup = input.getSharedRAbundVectors(lastLabel);
352                 
353                 m->mothurOut(lookup[0]->getLabel()); m->mothurOutEndLine();
354                 
355                 createList(lookup);
356                 
357                 for (int i = 0; i < lookup.size(); i++) {  delete lookup[i];  }
358             }
359         }else {
360             ListVector* list = input.getListVector();
361             string lastLabel = list->getLabel();
362             
363             //if the users enters label "0.06" and there is no "0.06" in their file use the next lowest label.
364             set<string> processedLabels;
365             set<string> userLabels = labels;
366             
367             //as long as you are not at the end of the file or done wih the lines you want
368             while((list != NULL) && ((allLines == 1) || (userLabels.size() != 0))) {
369                 
370                 if (m->control_pressed) { delete list;  for (int i = 0; i < outputNames.size(); i++) { m->mothurRemove(outputNames[i]); } return 0; }
371                 
372                 if(allLines == 1 || labels.count(list->getLabel()) == 1){                       
373                     
374                     m->mothurOut(list->getLabel()); m->mothurOutEndLine();
375                     
376                     createList(list);
377                     
378                     processedLabels.insert(list->getLabel());
379                     userLabels.erase(list->getLabel());
380                 }
381                 
382                 if ((m->anyLabelsToProcess(list->getLabel(), userLabels, "") == true) && (processedLabels.count(lastLabel) != 1)) {
383                     string saveLabel = list->getLabel();
384                     
385                     delete list; 
386                     list = input.getListVector(lastLabel);
387                     m->mothurOut(list->getLabel()); m->mothurOutEndLine();
388                     
389                     createList(list);
390                     
391                     processedLabels.insert(list->getLabel());
392                     userLabels.erase(list->getLabel());
393                     
394                     //restore real lastlabel to save below
395                     list->setLabel(saveLabel);
396                 }
397                 
398                 lastLabel = list->getLabel();
399                 //prevent memory leak
400                 delete list; list = NULL;
401                 
402                 if (m->control_pressed) { for (int i = 0; i < outputNames.size(); i++) { m->mothurRemove(outputNames[i]); }  return 0; }
403                 
404                 //get next line to process
405                 list = input.getListVector();                           
406             }
407             
408             if (m->control_pressed) {  for (int i = 0; i < outputNames.size(); i++) { m->mothurRemove(outputNames[i]); }  return 0; }
409             
410             //output error messages about any remaining user labels
411             set<string>::iterator it;
412             bool needToRun = false;
413             for (it = userLabels.begin(); it != userLabels.end(); it++) {  
414                 m->mothurOut("Your file does not include the label " + *it); 
415                 if (processedLabels.count(lastLabel) != 1) {
416                     m->mothurOut(". I will use " + lastLabel + "."); m->mothurOutEndLine();
417                     needToRun = true;
418                 }else {
419                     m->mothurOut(". Please refer to " + lastLabel + "."); m->mothurOutEndLine();
420                 }
421             }
422             
423             //run last label if you need to
424             if (needToRun == true)  {
425                 delete list;  
426                 list = input.getListVector(lastLabel);
427                 
428                 m->mothurOut(list->getLabel()); m->mothurOutEndLine();
429                 
430                 createList(list);
431                 
432                 delete list;
433             }
434         }
435         
436         if (m->control_pressed) { for (int i = 0; i < outputNames.size(); i++) { m->mothurRemove(outputNames[i]); }  return 0; }
437         
438         //output files created by command
439                 m->mothurOutEndLine();
440                 m->mothurOut("Output File Names: "); m->mothurOutEndLine();
441                 for (int i = 0; i < outputNames.size(); i++) {  m->mothurOut(outputNames[i]); m->mothurOutEndLine();    }
442                 m->mothurOutEndLine();
443         return 0;
444                 
445     }
446         catch(exception& e) {
447                 m->errorOut(e, "ListOtuLabelsCommand", "execute");
448                 exit(1);
449         }
450 }
451 //**********************************************************************************************************************
452
453 int ListOtuLabelsCommand::createList(vector<SharedRAbundVector*>& lookup){
454         try {
455         
456         map<string, string> variables; 
457         variables["[filename]"] = outputDir + m->getRootName(m->getSimpleName(inputFileName));
458         variables["[distance]"] = lookup[0]->getLabel();
459         string outputFileName = getOutputFileName("otulabels",variables);
460         outputNames.push_back(outputFileName);  outputTypes["otulabels"].push_back(outputFileName);
461                 ofstream out;
462                 m->openOutputFile(outputFileName, out);
463         
464         for (int i = 0; i < m->currentSharedBinLabels.size(); i++) {  out << m->currentSharedBinLabels[i] << endl;  }
465         
466         out.close();
467         
468         return 0;
469     }
470         catch(exception& e) {
471                 m->errorOut(e, "ListOtuLabelsCommand", "createList");
472                 exit(1);
473         }
474 }
475
476 //**********************************************************************************************************************
477
478 int ListOtuLabelsCommand::createList(vector<SharedRAbundFloatVector*>& lookup){
479         try {
480         map<string, string> variables; 
481         variables["[filename]"] = outputDir + m->getRootName(m->getSimpleName(inputFileName));
482         variables["[distance]"] = lookup[0]->getLabel();
483         string outputFileName = getOutputFileName("otulabels",variables);
484         outputNames.push_back(outputFileName);  outputTypes["accnos"].push_back(outputFileName);
485                 ofstream out;
486                 m->openOutputFile(outputFileName, out);
487         
488         for (int i = 0; i < m->currentSharedBinLabels.size(); i++) {  out << m->currentSharedBinLabels[i] << endl;  }
489         
490         out.close();
491         
492         return 0;
493     }
494         catch(exception& e) {
495                 m->errorOut(e, "ListOtuLabelsCommand", "createList");
496                 exit(1);
497         }
498 }
499 //**********************************************************************************************************************
500 int ListOtuLabelsCommand::createList(ListVector*& list){
501         try {
502         map<string, string> variables; 
503         variables["[filename]"] = outputDir + m->getRootName(m->getSimpleName(inputFileName));
504         variables["[distance]"] = list->getLabel();
505         string outputFileName = getOutputFileName("otulabels",variables);
506         outputNames.push_back(outputFileName);  outputTypes["accnos"].push_back(outputFileName);
507                 ofstream out;
508                 m->openOutputFile(outputFileName, out);
509         
510         vector<string> binLabels = list->getLabels();
511         for (int i = 0; i < binLabels.size(); i++) {  out << binLabels[i] << endl;  }
512
513         out.close();
514         
515         return 0;
516     }
517         catch(exception& e) {
518                 m->errorOut(e, "ListOtuLabelsCommand", "createList");
519                 exit(1);
520         }
521 }
522
523 //**********************************************************************************************************************
524