Main Page | Modules | Namespace List | Class Hierarchy | Alphabetical List | Class List | Directories | File List | Namespace Members | Class Members | File Members | Related Pages

TestAcc.cc

Go to the documentation of this file.
00001 #include <iostream> //System includes
00002 #include <fstream>
00003 #include <vector>
00004 #include <string.h>
00005 #include <stdio.h>
00006 
00007 #include "TVector3.h" //ROOT includes
00008 #include "TNtuple.h"
00009 #include "TFile.h"
00010 
00011 #include "MessageService/MsgService.h"
00012 #include "BField/BfldValidate.h" //BField headers
00013 #include "BField/BfldLoanPool.h"
00014 #include "BField/BField.h"
00015 
00016 #include "TestConstants.h" //My own headers
00017 
00018 CVSID("$Id: TestAcc.cc,v 1.2 2001/08/15 18:57:27 agoldst Exp $");
00019 
00020 const int kDefaultNumAccTestPts = 3012;
00021 
00022 const char kRectDataName[] = "rectData";
00023 const char kVorDataName[] = "vorData";
00024 
00025 void BenchmarkAccuracy(const char *outFileName,const char *rectMapFileName,
00026                        const char *vorMapFileName,const char *vorMeshFileName,
00027                        const char *vorBFldFileName,
00028                        const char *rectAccTestPtsFileName,
00029                        const char *vorAccTestPtsFileName);
00030 bool GetAccTestPts(vector<TVector3> &pts,vector<TVector3> &bfld,
00031                    const char *fileName);
00032 void AccTest(const vector<TVector3> &pts,const vector<TVector3> &trueB,
00033              BField *field,TNtuple *outData,int algorithm);
00034 
00035 int GetNumPointsRect(const char *fileName);
00036 int GetNumPointsVor(const char *fileName);
00037 BField *NewBFieldRect(const char *mapFileName);
00038 BField *NewBFieldVor(const char *vorMapFileName,const char *meshFileName,
00039                      const char *vorBFieldFileName);
00040 
00041 //define WRITE_OUT_BIG_ERR_PTS
00042 
00043 #ifdef WRITE_OUT_BIG_ERR_PTS
00044 const double kSmallestBigErr = 0.10; //10% is big!
00045 
00046 ofstream *gBigErrPtsFile;
00047 #endif
00048 
00049 void BenchmarkAccuracy(const char *outFileName,const char *rectMapFileName,
00050                        const char *vorMapFileName,const char *vorMeshFileName,
00051                        const char *vorBFldFileName,
00052                        const char *rectAccTestPtsFileName,
00053                        const char *vorAccTestPtsFileName) {
00054 
00055   MSG("Bfldtest",Msg::kDebug) << "Running accuracy test..." << endl;
00056 
00057   TFile outFile(outFileName,"RECREATE"); //Root datafile to store results.
00058 
00059   vector<TVector3> testPts(kDefaultNumAccTestPts);
00060   vector<TVector3> testField(kDefaultNumAccTestPts);
00061   
00062   BField *theRectField, *theVorField;
00063   TNtuple *theData; //Ntuple to store data as we go
00064 
00065 #ifdef WRITE_OUT_BIG_ERR_PTS
00066   gBigErrPtsFile = new ofstream("bigErrPts.bfb",ios::out);
00067 #endif
00068 
00069   MSG("Bfldtest",Msg::kDebug) << "Building rect2d BField using file "
00070                               << rectMapFileName << endl;
00071 
00072   theRectField = NewBFieldRect(rectMapFileName);
00073   
00074   if(!GetAccTestPts(testPts,testField,rectAccTestPtsFileName)) {
00075     MSG("Bfldtest",Msg::kWarning)
00076       << "Problem reading in rect2d test point file. Bailing." << endl;
00077     return;
00078   }
00079 
00080   theData = new TNtuple(kRectDataName,kRectDataName,
00081                         "x:y:z:btx:bty:btz:brcx:brcy:brcz:brbx:brby:brbz:brpx:brpy:brpz:brvx:brvy:brvz");
00082 
00083   //Translation:
00084   //First letter is 'b' for magnetic field.
00085   //Second letter is algorithm, 'r' for rect and 'v' for vor
00086   //Third letter is interpolation method's first letter exc.
00087   //PlanarVec, which is 'v'.
00088   //Fourth letter is component of the vector.
00089 
00090   AccTest(testPts,testField,theRectField,theData,kAlgRect);
00091 
00092   MSG("Bfldtest",Msg::kDebug) << "Saving Ntuple " << kRectDataName << endl;
00093 
00094   //Because TFile::Write will write whatever ntuples are in memory to disk,
00095   //we have to remove the rect2d data ntuple from memory before we build
00096   //and write the Voronoi data ntuple.
00097 
00098   outFile.Write();
00099   delete theData;
00100   delete theRectField;
00101 
00102   MSG("Bfldtest",Msg::kDebug)
00103     << "Building Voronoi BField using the following: " << endl;
00104   MSG("Bfldtest",Msg::kDebug) << "Voronoi diagram: " << vorMapFileName << endl;
00105   MSG("Bfldtest",Msg::kDebug) << "Voronoi mesh: " << vorMeshFileName << endl;
00106   MSG("Bfldtest",Msg::kDebug) << "Generator BField data: "
00107                               << vorBFldFileName << endl;
00108   
00109   theVorField = NewBFieldVor(vorMapFileName,vorMeshFileName,
00110                              vorBFldFileName);
00111   
00112   if(!GetAccTestPts(testPts,testField,vorAccTestPtsFileName)) {
00113     MSG("Bfldtest",Msg::kWarning)
00114       << "Problem reading in Voronoi test point file. Bailing." << endl;
00115     return;
00116   }
00117 
00118   theData = new TNtuple(kVorDataName,kVorDataName,
00119                         "x:y:z:btx:bty:btz:bvcx:bvcy:bvcz:bvpx:bvpy:bvpz");
00120 
00121   AccTest(testPts,testField,theVorField,theData,kAlgVor);
00122   
00123   MSG("Bfldtest",Msg::kDebug) << "Saving Ntuple " << kVorDataName << endl;
00124 
00125   outFile.Write();
00126   delete theData;
00127   delete theVorField;
00128 
00129   MSG("Bfldtest",Msg::kInfo) << "Done with accuracy test." << endl;
00130   MSG("Bfldtest",Msg::kInfo) << "Output written to " << outFileName << endl;
00131 }
00132 
00133 void AccTest(const vector<TVector3> &pts,const vector<TVector3> &trueB,
00134              BField *field,TNtuple *outData,int algorithm) {
00135   if(algorithm == kAlgRect) {
00136     MSG("Bfldtest",Msg::kDebug)
00137       << "Running accuracy test for rect2d algorithm..." << endl;
00138   }
00139   else {
00140     MSG("Bfldtest",Msg::kDebug)
00141       << "Running accuracy test for Voronoi algorithm..." << endl;
00142   }
00143 
00144   int i,j;
00145   TVector3 r,bt,brc,brb,brp,brv,bvc,bvp;
00146   float *row;
00147 
00148   //***Is BField smart enough to handle a change in interpolation
00149   //methods in mid-run?
00150   //I suspect not...in principle, though, it ought to work.
00151 
00152   //Write out the data into the ntuple, in the ugliest possible way.
00153 
00154   for(i = 0;i < pts.size();i++) {
00155     r = pts[i];
00156     bt = trueB[i];
00157 
00158     j = 0;
00159     if(algorithm == kAlgRect) {
00160       row = new float[18];
00161     }
00162     else {
00163       row = new float[12];
00164     }
00165 
00166     row[j] = r.X(); ++j;
00167     row[j] = r.Y(); ++j;
00168     row[j] = r.Z(); ++j;
00169     
00170     row[j] = bt.X(); ++j;
00171     row[j] = bt.Y(); ++j;
00172     row[j] = bt.Z(); ++j;
00173 
00174 
00175     if(algorithm == kAlgRect) {
00176       field->SetInterpMethod(BfldInterpMethod::kClosest);
00177       brc = field->GetBField(r);
00178       field->SetInterpMethod(BfldInterpMethod::kBilinear);
00179       brb = field->GetBField(r);
00180       field->SetInterpMethod(BfldInterpMethod::kPlanar);
00181       brp = field->GetBField(r);
00182       field->SetInterpMethod(BfldInterpMethod::kPlanarVec);
00183       brv = field->GetBField(r);
00184    
00185       row[j] = brc.X(); ++j;
00186       row[j] = brc.Y(); ++j;
00187       row[j] = brc.Z(); ++j;
00188       
00189       row[j] = brb.X(); ++j;
00190       row[j] = brb.Y(); ++j;
00191       row[j] = brb.Z(); ++j;
00192       
00193       row[j] = brp.X(); ++j;
00194       row[j] = brp.Y(); ++j;
00195       row[j] = brp.Z(); ++j;
00196       
00197       row[j] = brv.X(); ++j;
00198       row[j] = brv.Y(); ++j;
00199       row[j] = brv.Z();
00200     
00201 
00202 #ifdef WRITE_OUT_BIG_ERR_PTS
00203       double err = (brb-bt).Mag() / bt.Mag();
00204       if(err > kSmallestBigErr) {
00205         *gBigErrPtsFile << "r " << r.X() << " " << r.Y()
00206                         << " " << err << endl;
00207       }
00208 #endif
00209 
00210     }
00211     else { //so algorithm == kAlgVor
00212       field->SetInterpMethod(BfldInterpMethod::kClosest);
00213       bvc = field->GetBField(r);
00214       field->SetInterpMethod(BfldInterpMethod::kPlanar);
00215       bvp = field->GetBField(r);
00216     
00217       row[j] = bvc.X(); ++j;
00218       row[j] = bvc.Y(); ++j;
00219       row[j] = bvc.Z(); ++j;
00220 
00221       row[j] = bvp.X(); ++j;
00222       row[j] = bvp.Y(); ++j;
00223       row[j] = bvp.Z();
00224 
00225 #ifdef WRITE_OUT_BIG_ERR_PTS
00226       double err = (bvp-bt).Mag() / bt.Mag();
00227       if(err > kSmallestBigErr) {
00228         *gBigErrPtsFile << "v " << r.X() << " " << r.Y()
00229                         << " " << err << endl;
00230       }
00231 #endif
00232     } 
00233 
00234     outData->Fill(row);
00235     delete row;
00236   }
00237 }
00238 
00239 bool GetAccTestPts(vector<TVector3> &pts,vector<TVector3> &bfld,
00240                    const char *fileName) {
00241   //Read the data from fileName into pts and bfld
00242   //For now, assume the data will have the form of an ANSYS output file,
00243   //to wit, a series of lines of the form
00244   //id  x  y  z bx  by  bz
00245   //where all variables (including id) are floats
00246 
00247   MSG("Bfldtest",Msg::kDebug)
00248     << "Reading in test points file " << fileName << endl;
00249 
00250   ifstream inFile(fileName,ios::in);
00251   if(!inFile.good()) {
00252     MSG("Bfldtest",Msg::kWarning)
00253       << "Error opening test points file " << fileName << endl;
00254     return false;
00255   }
00256 
00257   if(pts.size() > bfld.size()) //Make sure the arrays match in size.
00258     bfld.resize(pts.size());
00259   else
00260     pts.resize(bfld.size());
00261   int n = pts.size();
00262 
00263   float id_ignored,x,y,z,bx,by,bz;
00264   int i = 0;
00265 
00266   while(!inFile.eof()) {
00267     inFile >> id_ignored >> x >> y >> z >> bx >> by >> bz;
00268     if(i >= n) { //The poor man's dynamically resizing array.
00269       n *= 2;
00270       pts.resize(n);
00271       bfld.resize(n);
00272     }
00273 
00274     pts[i].SetXYZ(x,y,z);
00275     bfld[i].SetXYZ(bx,by,bz);
00276     i++;
00277   }
00278 
00279   pts.resize(i); //Truncate the arrays to exactly the number
00280   bfld.resize(i); //of points read in.
00281 
00282   MSG("Bfldtest",Msg::kDebug)
00283     << "Read in " << i << " test points and B values." << endl;
00284   return true;
00285 }

Generated on Mon Feb 15 11:07:41 2010 for loon by  doxygen 1.3.9.1