34   Equalization::Equalization() {
 
   50     loadInputs(fromListName);
 
   57   Equalization::~Equalization() {
 
   59     clearNormalizations();
 
   60     clearOverlapStatistics();
 
   62     if (m_results != NULL) {
 
   78   void Equalization::addHolds(QString holdListName) {
 
   82     if (holdList.size() > m_imageList.size()) {
 
   83       QString msg = 
"The list of identifiers to be held must be less than or ";
 
   84       msg += 
"equal to the total number of identitifers.";
 
   89     for (
int i = 0; i < holdList.size(); i++) {
 
   91       for (
int j = 0; j < m_imageList.size(); j++) {
 
   92         if (holdList[i] == m_imageList[j]) {
 
   94           m_holdIndices.push_back(j);
 
   99         QString msg = 
"The hold list file [" + holdList[i].toString() +
 
  100                           "] does not match a file in the from list";
 
  130   void Equalization::calculateStatistics(
double percent, 
int mincnt, 
bool wtopt,
 
  137     m_samplingPercent = percent;
 
  139     m_lsqMethod = methodType;
 
  142     if (!m_recalculating) {
 
  143       calculateBandStatistics();
 
  146     calculateOverlapStatistics();
 
  149     for (
int img = 0; img < m_imageList.size(); img++) {
 
  151       if (!m_doesOverlapList[img]) {
 
  152         m_badFiles += m_imageList[img].toString();
 
  155     if (!m_badFiles.isEmpty()) {
 
  161       msg = 
"There are input images that do not overlap with enough valid pixels. ";
 
  162       msg += 
"See application log or \"NonOverlaps\" keyword in output statistics file.";
 
  168       for (
int band = 0; band < m_maxBand; band++) {
 
  169         m_overlapNorms[band]->Solve(m_sType, methodType);
 
  171         for (
unsigned int img = 0; img < m_adjustments.size(); img++) {
 
  172           m_adjustments[img]->addGain(m_overlapNorms[band]->Gain(img));
 
  173           if (qFuzzyCompare(m_overlapNorms[band]->Gain(img), 0.0)) { 
 
  175             cout << band << endl;
 
  176             cout << m_overlapNorms[band]->Gain(img) << endl;
 
  179                              "Calculation for equalization statistics failed. Gain = 0.",
 
  182           m_adjustments[img]->addOffset(m_overlapNorms[band]->Offset(img));
 
  183           m_adjustments[img]->addAverage(m_overlapNorms[band]->
Average(img));
 
  186       m_normsSolved = 
true;
 
  190       QString msg = 
"Unable to calculate the equalization statistics. You may " 
  191       "want to try another LeastSquares::SolveMethod.";
 
  206   void Equalization::calculateBandStatistics() {
 
  209     for (
int band = 1; band <= m_maxBand; band++) {
 
  211       vector<Statistics *> statsList;
 
  212       for (
int img = 0; img < (int) m_imageList.size(); img++) {
 
  215         QString statMsg = 
"Calculating Statistics for Band " + bandStr +
 
  220         QString inp = m_imageList[img].toString();
 
  229         statsList.push_back(stats);
 
  235       m_overlapNorms.push_back(oNorm);
 
  246   void Equalization::calculateOverlapStatistics() {
 
  248     for (
int img = 0; img < m_imageList.size(); img++) {
 
  254     for (
int i = 0; i < m_imageList.size(); i++) {
 
  258       for (
int j = (i + 1); j < m_imageList.size(); j++) {
 
  260         if (m_alreadyCalculated[i] == 
true && m_alreadyCalculated[j] == 
true) {
 
  269         QString cubeStr1 = 
toString((
int)(i + 1));
 
  270         QString cubeStr2 = 
toString((
int)(j + 1));
 
  271         QString statMsg = 
"Gathering Overlap Statisitcs for Cube " +
 
  272                          cubeStr1 + 
" vs " + cubeStr2 + 
" of " +
 
  280           m_overlapStats.push_back(oStats);
 
  282           for (
int band = 1; band <= m_maxBand; band++) {
 
  290               m_overlapNorms[band - 1]->AddOverlap(
 
  293               m_doesOverlapList[i] = 
true;
 
  294               m_doesOverlapList[j] = 
true;
 
  302     for (
unsigned int o = 0; o < m_overlapStats.size(); o++) {
 
  303       for (
int band = 1; band <= m_maxBand; band++) {
 
  304         (m_overlapStats[o]->IsValid(band)) ? m_validCnt++ : m_invalidCnt++;
 
  318   void Equalization::setResults() {
 
  319     if (m_results != NULL) {
 
  324     m_results = 
new Pvl();
 
  325     m_results->setTerminator(
"");
 
  327     PvlObject equ(
"EqualizationInformation");
 
  334     gen += 
PvlKeyword(
"Weighted", (m_wtopt) ? 
"true" : 
"false");
 
  335     int solType = m_sType;
 
  336     int lsqMethod = m_lsqMethod;
 
  340     for (
int img = 0; img < m_badFiles.size(); img++) {
 
  341       nonOverlaps += m_badFiles[img];
 
  344     gen += 
PvlKeyword(
"HasCorrections", (m_normsSolved) ? 
"true" : 
"false");
 
  348     for (
int img = 0; img < m_imageList.size(); img++) {
 
  351       norm.addComment(
"Formula: newDN = (oldDN - AVERAGE) * GAIN + AVERAGE + OFFSET");
 
  352       norm.addComment(
"BandN = (GAIN, OFFSET, AVERAGE)");
 
  353       norm += 
PvlKeyword(
"FileName", m_imageList[img].original());
 
  357         for (
int band = 1; band <= m_maxBand; band++) {
 
  358           QString mult = 
toString(m_adjustments[img]->getGain(band - 1));
 
  359           QString base = 
toString(m_adjustments[img]->getOffset(band - 1));
 
  360           QString avg = 
toString(m_adjustments[img]->getAverage(band - 1));
 
  362           QString bandStr = 
"Band" + bandNum;
 
  374     m_results->addObject(equ);
 
  377     for (
unsigned int i = 0; i < m_overlapStats.size(); i++) {
 
  378       PvlObject oStat = m_overlapStats[i]->toPvl();
 
  379       m_results->
addObject(m_overlapStats[i]->toPvl());
 
  393   void Equalization::recalculateStatistics(QString instatsFileName) {
 
  394     m_recalculating = 
true;
 
  395     Pvl inStats(instatsFileName);
 
  397     calculateStatistics(m_samplingPercent, m_mincnt, m_wtopt, m_lsqMethod);
 
  412   void Equalization::importStatistics(QString instatsFileName) {
 
  415     QVector<int> normIndices = validateInputStatistics(instatsFileName);
 
  416     Pvl inStats(instatsFileName);
 
  422     if (!general.
hasKeyword(
"HasCorrections") || general[
"HasCorrections"][0] == 
"true") {
 
  423       m_normsSolved = 
true;
 
  426       for (
int img = 0; img < (int) m_imageList.size(); img++) {
 
  435         for (
int band = 1; band < normalization.
keywords(); band++) {
 
  436           adjustment->addGain(
toDouble(normalization[band][0]));
 
  437           adjustment->addOffset(
toDouble(normalization[band][1]));
 
  438           adjustment->addAverage(
toDouble(normalization[band][2]));
 
  441         addAdjustment(adjustment);
 
  445       m_normsSolved = 
false;
 
  461   void Equalization::applyCorrection(QString toListName=
"") {
 
  463       QString msg = 
"Corrective factors have not yet been determined. ";
 
  464       if (m_badFiles.size() > 0) {
 
  465         msg += 
"Fix any non-overlapping images and recalculate the image statistics. ";
 
  466         msg += 
"File(s) without overlaps: ";
 
  467         for (
int img = 0; img < m_badFiles.size(); img++) {
 
  468           msg += 
" [" + m_badFiles[img] + 
"] ";
 
  472         msg += 
"Add more images to create more overlaps and recalculate, ";
 
  473         msg += 
"or try another solve method.";
 
  479     fillOutList(outList, toListName);
 
  481     QString maxCubeStr = 
toString((
int) m_imageList.size());
 
  482     for (
int img = 0; img < m_imageList.size(); img++) {
 
  486           " of " + maxCubeStr);
 
  490       const QString inp = m_imageList[img].toString();
 
  494       QString out = outList[img].toString();
 
  516     PvlGroup results = m_results->findObject(
"EqualizationInformation").findGroup(
"General");
 
  520       for (
int img = 0; img < m_imageList.size(); img++) {
 
  524         for (
int band = 1; band <= m_maxBand; band++) {
 
  525           QString mult = 
toString(m_adjustments[img]->getGain(band - 1));
 
  526           QString base = 
toString(m_adjustments[img]->getOffset(band - 1));
 
  527           QString avg = 
toString(m_adjustments[img]->getAverage(band - 1));
 
  529           QString bandStr = 
"Band" + bandNum;
 
  534           results += bandStats;
 
  547   void Equalization::write(QString outstatsFileName) {
 
  549     m_results->write(outstatsFileName);
 
  553   double Equalization::evaluate(
double dn, 
int imageIndex, 
int bandIndex)
 const {
 
  554     return m_adjustments[imageIndex]->evaluate(dn, bandIndex);
 
  567   void Equalization::loadInputs(QString fromListName) {
 
  569     m_imageList.read(fromListName);
 
  570     m_maxCube = m_imageList.size();
 
  572     if (m_imageList.size() < 2) {
 
  573       QString msg = 
"The input file [" + fromListName +
 
  574         "] must contain at least 2 file names";
 
  582     m_doesOverlapList.resize(m_imageList.size(), 
false);
 
  583     m_alreadyCalculated.resize(m_imageList.size(), 
false);
 
  585     errorCheck(fromListName);
 
  589   void Equalization::setInput(
int index, QString value) {
 
  590     m_imageList[index] = value;
 
  594   const FileList &Equalization::getInputs()
 const {
 
  599   void Equalization::fillOutList(FileList &outList, QString toListName) {
 
  600     if (toListName.isEmpty()) {
 
  601       generateOutputs(outList);
 
  604       loadOutputs(outList, toListName);
 
  615   void Equalization::errorCheck(QString fromListName) {
 
  616     for (
int i = 0; i < m_imageList.size(); i++) {
 
  620       for (
int j = (i + 1); j < m_imageList.size(); j++) {
 
  626           QString msg = 
"Number of bands do not match between cubes [" +
 
  627             m_imageList[i].toString() + 
"] and [" + m_imageList[j].toString() + 
"]";
 
  636         if (*proj1 != *proj2) {
 
  637           QString msg = 
"Mapping groups do not match between cubes [" +
 
  638             m_imageList[i].toString() + 
"] and [" + m_imageList[j].toString() + 
"]";
 
  649   void Equalization::generateOutputs(
FileList &outList) {
 
  650     for (
int img = 0; img < m_imageList.size(); img++) {
 
  652       QString filename = file.
path() + 
"/" + file.baseName() +
 
  653         ".equ." + file.extension();
 
  654       outList.push_back(
FileName(filename));
 
  667   void Equalization::loadOutputs(
FileList &outList, QString toListName) {
 
  671     if (outList.size() != m_imageList.size()) {
 
  672       QString msg = 
"Each input file in the FROM LIST must have a ";
 
  673       msg += 
"corresponding output file in the TO LIST.";
 
  679     for (
int i = 0; i < outList.size(); i++) {
 
  681         QString msg = 
"The to list file [" + outList[i].toString() +
 
  682           "] has the same name as its corresponding from list file.";
 
  690     for (
unsigned int h = 0; h < m_holdIndices.size(); h++)
 
  691       oNorm->
AddHold(m_holdIndices[h]);
 
  698   void Equalization::clearAdjustments() {
 
  699     for (
unsigned int adj = 0; adj < m_adjustments.size(); adj++) {
 
  700       delete m_adjustments[adj];
 
  702     m_adjustments.clear(); 
 
  714     m_adjustments.push_back(adjustment);
 
  721   void Equalization::clearNormalizations() {
 
  722     for (
unsigned int oNorm = 0; oNorm < m_overlapNorms.size(); oNorm++) {
 
  723       delete m_overlapNorms[oNorm];
 
  725     m_overlapNorms.clear();
 
  732   void Equalization::clearOverlapStatistics() {
 
  733     for (
unsigned int oStat = 0; oStat < m_overlapStats.size(); oStat++) {
 
  734       delete m_overlapStats[oStat];
 
  736     m_overlapStats.clear();
 
  745   void Equalization::addValid(
int count) {
 
  755   void Equalization::addInvalid(
int count) {
 
  756     m_invalidCnt += count;
 
  772     for (
int img = 0; img < m_imageList.size(); img++) {
 
  773       imgNames.append(m_imageList[img].name());
 
  779     m_samplingPercent = eqGen[
"SamplingPercent"];
 
  780     m_mincnt = eqGen[
"MinCount"];
 
  781     m_wtopt = (eqGen[
"Weighted"][0] == 
"true") ? 
true : 
false; 
 
  786     PvlObject::ConstPvlObjectIterator curObj = inStats.
beginObject();
 
  788       if (curObj->isNamed(
"OverlapStatistics")) {
 
  790         m_overlapStats.push_back(o);
 
  793         QString fileX = oStat[
"File1"][0];
 
  794         QString fileY = oStat[
"File2"][0];
 
  797         int x = imgNames.indexOf(fileX);
 
  798         int y = imgNames.indexOf(fileY);
 
  799         m_alreadyCalculated[x] = 
true;
 
  800         m_alreadyCalculated[y] = 
true;
 
  804         if (oStat[
"Valid"][0] == 
"true") {
 
  805           m_doesOverlapList[x] = 
true; 
 
  806           m_doesOverlapList[y] = 
true;
 
  813     calculateBandStatistics();
 
  821     for (
int o = 0; o < (int) m_overlapStats.size(); o++) {
 
  828       for (
int i = 0; i < m_imageList.size(); i++) {
 
  829         QString imageName(m_imageList[i].name());
 
  835           overlapIndices[o].push_front(i);
 
  840           overlapIndices[o].push_back(i);
 
  845     for (
int o = 0; o < (int) m_overlapStats.size(); o++) {
 
  847       for (
int band = 1; band <= oStat->
Bands(); band++) {
 
  851           m_overlapNorms[band-1]->AddOverlap(oStat->
GetMStats(band).
X(), overlapIndices[o][0],
 
  852                                              oStat->
GetMStats(band).
Y(), overlapIndices[o][1], weight);
 
  864   void Equalization::setSolved(
bool solved) {
 
  865     m_normsSolved = solved;
 
  874   bool Equalization::isSolved()
 const {
 
  875     return m_normsSolved;
 
  882   void Equalization::init() {
 
  887     m_samplingPercent = 100.0;
 
  893     m_sType = OverlapNormalization::Both;
 
  894     m_lsqMethod = LeastSquares::SPARSE;
 
  897     m_doesOverlapList.clear();
 
  898     m_alreadyCalculated.clear();
 
  899     m_normsSolved = 
false;
 
  900     m_recalculating = 
false;
 
  921   QVector<int> Equalization::validateInputStatistics(QString instatsFileName) {
 
  924     Pvl inStats(instatsFileName);
 
  928     if (m_imageList.size() > equalInfo.
groups() - 1) {
 
  929       QString msg = 
"Each input file in the FROM LIST must have a ";
 
  930       msg += 
"corresponding input file in the INPUT STATISTICS.";
 
  935     for (
int i = 0; i < m_imageList.size(); i++) {
 
  936       QString fromFile = m_imageList[i].original();
 
  937       bool foundFile = 
false;
 
  938       for (
int j = 1; j < equalInfo.
groups(); j++) {
 
  940         QString normFile  = normalization[
"FileName"][0];
 
  941         if (fromFile == normFile) {
 
  945           normIndices.push_back(j);
 
  950         QString msg = 
"The from list file [" + fromFile +
 
  951                           "] does not have any corresponding file in the stats list.";
 
  960   void Equalization::CalculateFunctor::operator()(
Buffer &in)
 const {
 
  968   void Equalization::CalculateFunctor::addStats(Buffer &in)
 const {
 
  970     m_stats->AddData(&in[0], in.size());
 
  974   void Equalization::ApplyFunctor::operator()(Buffer &in, Buffer &out)
 const {
 
  975     int index = in.Band() - 1;
 
  976     for (
int i = 0; i < in.size(); i++) {
 
  978         in[i] : m_adjustment->evaluate(in[i], index);
 
Buffer for reading and writing cube data. 
 
void SetMincount(unsigned int mincnt)
Sets the minimum number of valid pixels for the overlap to be considered valid for PVL output...
 
int Line(const int index=0) const 
Returns the line position associated with a shape buffer index. 
 
void ProcessCubeInPlace(const Functor &funct, bool threaded=true)
Same functionality as StartProcess(void funct(Isis::Buffer &inout)) using Functors. 
 
void EndProcess()
End the processing sequence and cleans up by closing cubes, freeing memory, etc. 
 
int Bands() const 
Returns the number of bands both cubes have. 
 
int LineDimension() const 
Returns the number of lines in the shape buffer. 
 
This class is used as a functor calculate image statistics. 
 
PvlGroupIterator findGroup(const QString &name, PvlGroupIterator beg, PvlGroupIterator end)
Find a group with the specified name, within these indexes. 
 
PvlObjectIterator endObject()
Returns the index of the ending object. 
 
Isis::Cube * SetInputCube(const QString ¶meter, const int requirements=0)
Opens an input cube specified by the user and verifies requirements are met. 
 
File name manipulation and expansion. 
 
bool HasOverlap(int band) const 
Checks the specified band for an overlap. 
 
PvlObjectIterator findObject(const QString &name, PvlObjectIterator beg, PvlObjectIterator end)
Find the index of object with a specified name, between two indexes. 
 
int keywords() const 
Returns the number of keywords contained in the PvlContainer. 
 
virtual Cube * SetOutputCube(const QString &fname, const CubeAttributeOutput &att)
Create the output file. 
 
void addGroup(const Isis::PvlGroup &group)
Add a group to the object. 
 
Internalizes a list of files. 
 
SolutionType
Enumeration for whether user/programmer wants to calculate new gains, offsets, or both when solving...
 
QString toString(bool boolToConvert)
Global function to convert a boolean to a string. 
 
Projection * projection()
 
This class is used as a functor to apply adjustments (equalize) to an image. 
 
double toDouble(const QString &string)
Global function to convert from a string to a double. 
 
void AddHold(unsigned holdIndex)
Sets the list of files to be held during the solving process. 
 
void addObject(const PvlObject &object)
Add a PvlObject. 
 
This class is used to accumulate statistics on double arrays. 
 
Isis::FileName FileNameX() const 
Returns the filename of the first cube. 
 
Base class for Map Projections. 
 
Calculate the bases and multipliers for normalizing overlapping "data sets" (e.g., cubes). 
 
void read(FileName listFile)
Constructs a FileList from a stream. 
 
void SetText(const QString &text)
Changes the value of the text string reported just before 0% processed. 
 
Contains multiple PvlContainers. 
 
#define _FILEINFO_
Macro for the filename and line number. 
 
Manipulate and parse attributes of output cube filenames. 
 
A single keyword-value pair. 
 
int bandCount() const 
Returns the number of virtual bands for the cube. 
 
bool IsSpecial(const double d)
Returns if the input pixel is special. 
 
void open(const QString &cfile, QString access="r")
This method will open an isis cube for reading or reading/writing. 
 
Isis::MultivariateStatistics GetMStats(int band) const 
Returns the MultivariateStatistics object containing all the data from both cubes in the overlapping ...
 
Container for cube-like labels. 
 
Isis::Progress * Progress()
This method returns a pointer to a Progress object. 
 
Isis::Statistics X() const 
Returns a Stats object for all of the X data fed through the AddData method. 
 
Isis::FileName FileNameY() const 
Returns the filename of the second cube. 
 
Calculates statistics in the area of overlap between two projected cubes. 
 
int groups() const 
Returns the number of groups contained. 
 
PvlGroup & group(const int index)
Return the group at the specified index. 
 
Isis::Statistics Y() const 
Returns a Stats object for all of the Y data fed through the AddData method. 
 
void ProcessCube(const Functor &funct, bool threaded=true)
Same functionality as StartProcess(void funct(Isis::Buffer &in, Isis::Buffer &out)) using Functors...
 
BigInt ValidPixels() const 
Returns the number of valid pixels processed. 
 
Contains Pvl Groups and Pvl Objects. 
 
PvlObjectIterator beginObject()
Returns the index of the beginning object. 
 
QString path() const 
Returns the path. 
 
bool hasKeyword(const QString &name) const 
Check to see if a keyword exists. 
 
Functor for reduce using average functionality. 
 
IO Handler for Isis Cubes.