// Action_FilterByData::Init() Action::RetType Action_FilterByData::Init(ArgList& actionArgs, ActionInit& init, int debugIn) { maxmin_ = init.DSL().AddSet( DataSet::INTEGER, actionArgs.GetStringKey("name"), "Filter" ); if (maxmin_ == 0) return Action::ERR; DataFile* maxminfile = init.DFL().AddDataFile( actionArgs.GetStringKey("out"), actionArgs ); if (maxminfile != 0) maxminfile->AddDataSet( maxmin_ ); // Get min and max args. while (actionArgs.Contains("min")) Min_.push_back( actionArgs.getKeyDouble("min", 0.0) ); while (actionArgs.Contains("max")) Max_.push_back( actionArgs.getKeyDouble("max", 0.0) ); if (Min_.empty()) { mprinterr("Error: At least one 'min' arg must be specified.\n"); return Action::ERR; } if (Max_.empty()) { mprinterr("Error: At least one 'max' arg must be specified.\n"); return Action::ERR; } if (Min_.size() != Max_.size()) { mprinterr("Error: # of 'min' args (%zu) != # of 'max' args (%zu)\n", Min_.size(), Max_.size()); return Action::ERR; } // Get DataSets from remaining arguments Dsets_.AddSetsFromArgs( actionArgs.RemainingArgs(), init.DSL() ); if (Dsets_.empty()) { mprinterr("Error: No data sets specified.\n"); return Action::ERR; } if ( Dsets_.size() < Min_.size() ) { mprinterr("Error: More 'min'/'max' args (%zu) than data sets (%zu).\n", Min_.size(), Dsets_.size()); return Action::ERR; } if ( Dsets_.size() > Min_.size() ) { unsigned int Nremaining = Dsets_.size() - Min_.size(); double useMin = Min_.back(); double useMax = Max_.back(); mprintf("Warning: More data sets than 'min'/'max' args.\n" "Warning: Using min=%f and max=%f for last %zu data sets.\n", useMin, useMax, Nremaining); for (unsigned int ds = 0; ds < Nremaining; ++ds) { Min_.push_back( useMin ); Max_.push_back( useMax ); } } mprintf(" FILTER: Filtering out frames using %zu data sets.\n", Dsets_.size()); for (unsigned int ds = 0; ds < Dsets_.size(); ds++) mprintf("\t%.4f < '%s' < %.4f\n", Min_[ds], Dsets_[ds]->legend(), Max_[ds]); if (maxminfile != 0) mprintf("\tFilter frame info will be written to %s\n", maxminfile->DataFilename().full()); return Action::OK; }
/** Expect lowest replica file name to be passed in. 'remdtraj' should have * already been parsed out of input arguments. */ int Trajin_Multi::SetupTrajRead(FileName const& tnameIn, ArgList& argIn, Topology *tparmIn) { // Set file name and topology pointer. if (SetTraj().SetNameAndParm(tnameIn, tparmIn)) return 1; REMDtraj_.ClearIOarray(); // Check for deprecated args if (argIn.hasKey("remdout")) { mprinterr("%s", TrajIOarray::DEPRECATED_remdout); return 1; } // Process REMD-specific arguments if (argIn.Contains("remdtrajidx")) { // Looking for specific indices ArgList indicesArg(argIn.GetStringKey("remdtrajidx"), ","); if (indicesArg.empty()) { mprinterr("Error: remdtrajidx expects comma-separated list of target indices in each\n" "Error: dimension, '<dim1 idx>,<dim2 idx>,...,<dimN idx>'. Indices start\n" "Error: from 1.\n"); return 1; } for (ArgList::const_iterator arg = indicesArg.begin(); // TODO: validInteger? arg != indicesArg.end(); ++arg) remdtrajidx_.push_back( convertToInteger( *arg ) ); targetType_ = ReplicaInfo::INDICES; } else if (argIn.Contains("remdtrajtemp")) { // Looking for target temperature remdtrajtemp_ = argIn.getKeyDouble("remdtrajtemp",0.0); targetType_ = ReplicaInfo::TEMP; } // Set up replica file names. if (REMDtraj_.SetupReplicaFilenames( tnameIn, argIn )) return 1; // Set up TrajectoryIO classes for all file names. if (REMDtraj_.SetupIOarray(argIn, SetTraj().Counter(), cInfo_, Traj().Parm())) return 1; // Check that replica dimension valid for desired indices. if (targetType_ == ReplicaInfo::INDICES && cInfo_.ReplicaDimensions().Ndims() != (int)remdtrajidx_.size()) { mprinterr("Error: Replica # of dim (%i) not equal to target # dim (%zu)\n", cInfo_.ReplicaDimensions().Ndims(), remdtrajidx_.size()); return 1; } // If target type is temperature make sure there is temperature info. if (targetType_ == ReplicaInfo::TEMP && !cInfo_.HasTemp()) { mprinterr("Error: Some or all replicas are missing temperature info.\n"); return 1; } return 0; }
// Action_Outtraj::Init() Action::RetType Action_Outtraj::Init(ArgList& actionArgs, ActionInit& init, int debugIn) { // Set up output traj outtraj_.SetDebug(debugIn); std::string trajfilename = actionArgs.GetStringNext(); if (trajfilename.empty()) { mprinterr("Error: No filename given.\nError: Usage: "); Help(); return Action::ERR; } associatedParm_ = init.DSL().GetTopology(actionArgs); if (associatedParm_ == 0) { mprinterr("Error: Could not get associated topology for %s\n",trajfilename.c_str()); return Action::ERR; } // If maxmin, get the name of the dataset as well as the max and min values. double lastmin = 0.0; double lastmax = 0.0; while ( actionArgs.Contains("maxmin") ) { std::string datasetName = actionArgs.GetStringKey("maxmin"); if (!datasetName.empty()) { DataSet* dset = init.DSL().GetDataSet(datasetName); if (dset==0) { mprintf("Error: maxmin: Could not get dataset %s\n",datasetName.c_str()); return Action::ERR; } else { // Currently only allow int, float, or double datasets if (dset->Type() != DataSet::INTEGER && dset->Type() != DataSet::FLOAT && dset->Type() != DataSet::DOUBLE) { mprinterr("Error: maxmin: Only int, float, or double dataset (%s) supported.\n", datasetName.c_str()); return Action::ERR; } Dsets_.push_back( (DataSet_1D*)dset ); Max_.push_back( actionArgs.getKeyDouble("max",lastmax) ); Min_.push_back( actionArgs.getKeyDouble("min",lastmin) ); lastmax = Max_.back(); lastmin = Min_.back(); } } else { mprinterr("Error: maxmin Usage: maxmin <setname> max <max> min <min>\n"); return Action::ERR; } } // Initialize output trajectory with remaining arguments if ( outtraj_.InitEnsembleTrajWrite(trajfilename, actionArgs.RemainingArgs(), TrajectoryFile::UNKNOWN_TRAJ, init.DSL().EnsembleNum()) ) return Action::ERR; isSetup_ = false; mprintf(" OUTTRAJ: Writing frames associated with topology '%s'\n", associatedParm_->c_str()); for (unsigned int ds = 0; ds < Dsets_.size(); ++ds) mprintf("\tmaxmin: Printing trajectory frames based on %g <= %s <= %g\n", Min_[ds], Dsets_[ds]->legend(), Max_[ds]); return Action::OK; }
// Traj_SQM::processWriteArgs() int Traj_SQM::processWriteArgs(ArgList& argIn) { if (argIn.Contains("charge")) { charge_ = argIn.getKeyInt( "charge", 0 ); chargeIsSet_ = true; } else chargeIsSet_ = false; return 0; }
// ParmFile::ReadTopology() int ParmFile::ReadTopology(Topology& Top, FileName const& fnameIn, ArgList const& argListIn, int debugIn) { if (fnameIn.empty()) { mprinterr("Error: No input topology name given.\n"); return 1; } if (!File::Exists( fnameIn )) { mprinterr("Error: Topology '%s' does not exist.\n", fnameIn.full()); return 1; } parmName_ = fnameIn; ArgList argIn = argListIn; ParmFormatType pfType; ParmIO* parmio = 0; Top.SetDebug( debugIn ); // Only force bond search when 'bondsearch' is specified. bool bondsearch = false; if (argIn.Contains("bondsearch")) { Top.SetOffset( argIn.getKeyDouble("bondsearch", -1.0) ); bondsearch = true; } // 'as' keyword specifies a format std::string as_arg = argIn.GetStringKey("as"); if (!as_arg.empty()) { pfType = (ParmFormatType)FileTypes::GetFormatFromString( PF_KeyArray, as_arg, UNKNOWN_PARM ); if (pfType == UNKNOWN_PARM) { mprinterr("Error: Topology format '%s' not recognized.\n", as_arg.c_str()); return 1; } parmio = (ParmIO*)FileTypes::AllocIO( PF_AllocArray, pfType, false ); } else parmio = DetectFormat( parmName_, pfType ); if (parmio == 0) { mprinterr("Error: Could not determine format of topology '%s'\n", parmName_.full()); return 1; } mprintf("\tReading '%s' as %s\n", parmName_.full(), FileTypes::FormatDescription(PF_AllocArray, pfType) ); parmio->SetDebug( debugIn ); if (parmio->processReadArgs(argIn)) return 1; int err = parmio->ReadParm( parmName_.Full(), Top); // Perform setup common to all parm files. if (err == 0) err = Top.CommonSetup(bondsearch || parmio->NeedsBondSearch()); else mprinterr("Error reading topology file '%s'\n", parmName_.full()); delete parmio; if (err > 0) return 1; return 0; }
// DataIO::ProcessCommonArgs() int DataIO::ProcessCommonArgs(ArgList &argIn) { if (argIn.hasKey("noxcol")) hasXcolumn_ = false; if (argIn.hasKey("noemptyframes")) printEmptyFrames_ = false; std::string label = argIn.GetStringKey("xlabel"); if (!label.empty()) x_label_ = label; xmin_ = argIn.getKeyDouble("xmin",xmin_); xstep_ = argIn.getKeyDouble("xstep",xstep_); if (argIn.Contains("time")) { xstep_ = argIn.getKeyDouble("time",xstep_); xmin_ = 0.0; xoffset_ = 1.0; } return 0; }
// Exec_DataSetCmd::Execute() Exec::RetType Exec_DataSetCmd::Execute(CpptrajState& State, ArgList& argIn) { RetType err = CpptrajState::OK; if (argIn.Contains("legend")) { // Set legend for one data set std::string legend = argIn.GetStringKey("legend"); DataSet* ds = State.DSL().GetDataSet( argIn.GetStringNext() ); if (ds == 0) return CpptrajState::ERR; mprintf("\tChanging legend '%s' to '%s'\n", ds->legend(), legend.c_str()); ds->SetLegend( legend ); // --------------------------------------------- } else if (argIn.hasKey("outformat")) { // Change double precision set output format err = ChangeOutputFormat(State, argIn); // --------------------------------------------- } else if (argIn.hasKey("remove")) { // Remove data sets by various criteria err = Remove(State, argIn); // --------------------------------------------- } else if (argIn.hasKey("makexy")) { // Combine values from two sets into 1 err = MakeXY(State, argIn); // --------------------------------------------- } else if (argIn.hasKey("make2d")) { // Create 2D matrix from 1D set err = Make2D(State, argIn); // --------------------------------------------- } else if (argIn.hasKey("vectorcoord")) { // Extract vector X/Y/Z coord as new set err = VectorCoord(State, argIn); // --------------------------------------------- } else if (argIn.hasKey("filter")) { // Filter points in data set to make new data set err = Filter(State, argIn); // --------------------------------------------- } else if (argIn.hasKey("cat")) { // Concatenate two or more data sets err = Concatenate(State, argIn); // --------------------------------------------- } else if (argIn.hasKey("droppoints")) { // Drop points from set err = ModifyPoints(State, argIn, true); // --------------------------------------------- } else if (argIn.hasKey("keeppoints")) { // Keep points in set err = ModifyPoints(State, argIn, false); // --------------------------------------------- } else if (argIn.hasKey("dim")) { // Modify dimension of set(s) err = ChangeDim(State, argIn); // --------------------------------------------- } else if (argIn.hasKey("invert")) { // Invert set(s) X/Y, create new sets err = InvertSets(State, argIn); // --------------------------------------------- } else { // Default: change mode/type for one or more sets. err = ChangeModeType(State, argIn); } return err; }
/** Set up histogram with specified data sets. */ Analysis::RetType Analysis_Hist::Setup(ArgList& analyzeArgs, AnalysisSetup& setup, int debugIn) { debug_ = debugIn; // Keywords std::string histname = analyzeArgs.GetStringKey("name"); outfilename_ = analyzeArgs.GetStringKey("out"); if (outfilename_.empty()) { mprinterr("Error: Hist: No output filename specified.\n"); return Analysis::ERR; } traj3dName_ = analyzeArgs.GetStringKey("traj3d"); traj3dFmt_ = TrajectoryFile::WriteFormatFromString( analyzeArgs.GetStringKey("trajfmt"), TrajectoryFile::AMBERTRAJ ); parmoutName_ = analyzeArgs.GetStringKey("parmout"); // Create a DataFile here so any DataFile arguments can be processed. If it // turns out later that native output is needed the DataFile will be removed. outfile_ = setup.DFL().AddDataFile(outfilename_, analyzeArgs); if (outfile_==0) return Analysis::ERR; Temp_ = analyzeArgs.getKeyDouble("free",-1.0); if (Temp_!=-1.0) calcFreeE_ = true; else calcFreeE_ = false; gnuplot_ = analyzeArgs.hasKey("gnu"); if (analyzeArgs.hasKey("norm")) normalize_ = NORM_SUM; else if (analyzeArgs.hasKey("normint")) normalize_ = NORM_INT; else normalize_ = NO_NORM; circular_ = analyzeArgs.hasKey("circular"); nativeOut_ = analyzeArgs.hasKey("nativeout"); if ( analyzeArgs.Contains("min") ) { default_min_ = analyzeArgs.getKeyDouble("min", 0.0); minArgSet_ = true; } if ( analyzeArgs.Contains("max") ) { default_max_ = analyzeArgs.getKeyDouble("max", 0.0); maxArgSet_ = true; } default_step_ = analyzeArgs.getKeyDouble("step", 0.0) ; default_bins_ = analyzeArgs.getKeyInt("bins", -1); calcAMD_ = false; std::string amdname = analyzeArgs.GetStringKey("amd"); if (!amdname.empty()) { DataSet* ds = setup.DSL().GetDataSet( amdname ); if (ds == 0) { mprinterr("Error: AMD data set %s not found.\n", amdname.c_str()); return Analysis::ERR; } if (ds->Ndim() != 1) { mprinterr("Error: AMD data set must be 1D.\n"); return Analysis::ERR; } amddata_ = (DataSet_1D*)ds; calcAMD_ = true; } // Treat all remaining arguments as dataset names. Do not set up dimensions // yet since the data sets may not be fully populated. ArgList dsetNames = analyzeArgs.RemainingArgs(); for ( ArgList::const_iterator setname = dsetNames.begin(); setname != dsetNames.end(); ++setname) { if (CheckDimension( *setname, setup.DSL() )) return Analysis::ERR; } // histdata contains the DataSets to be histogrammed if (histdata_.empty()) { mprinterr("Error: Hist: No datasets specified.\n"); return Analysis::ERR; } // Total # of dimensions for the histogram is the number of sets to be binned. N_dimensions_ = histdata_.size(); if (!nativeOut_) { switch ( N_dimensions_ ) { case 1: hist_ = setup.DSL().AddSet( DataSet::DOUBLE, histname, "Hist"); break; case 2: hist_ = setup.DSL().AddSet( DataSet::MATRIX_DBL, histname, "Hist"); break; // TODO: GRID_DBL case 3: hist_ = setup.DSL().AddSet( DataSet::GRID_FLT, histname, "Hist"); break; default: // FIXME: GET N DIMENSION CASE! mprintf("Warning: Histogram dimension > 3. DataSet/DataFile output not supported.\n"); nativeOut_ = true; } } // traj3d only supported with 3D histograms if (!traj3dName_.empty() && N_dimensions_ != 3) { mprintf("Warning: 'traj3d' only supported with 3D histograms.\n"); traj3dName_.clear(); parmoutName_.clear(); } if (!nativeOut_) { // DataFile output. Add DataSet to DataFile. if (hist_ == 0) { mprinterr("Error: Could not set up histogram data set.\n"); return Analysis::ERR; } outfile_->AddDataSet( hist_ ); } else { // Native output. Remove DataFile from DataFileList outfile_ = setup.DFL().RemoveDataFile( outfile_ ); native_ = setup.DFL().AddCpptrajFile( outfilename_, "Histogram output" ); if (native_ == 0) return Analysis::ERR; } mprintf("\tHist: %s: Set up for %zu dimensions using the following datasets:\n", outfilename_.c_str(), N_dimensions_); mprintf("\t[ "); for (std::vector<DataSet_1D*>::iterator ds=histdata_.begin(); ds!=histdata_.end(); ++ds) mprintf("%s ",(*ds)->legend()); mprintf("]\n"); if (calcAMD_) mprintf("\tPopulating bins using AMD boost from data set %s\n", amddata_->legend()); if (calcFreeE_) mprintf("\tFree energy in kcal/mol will be calculated from bin populations at %f K.\n",Temp_); if (nativeOut_) mprintf("\tUsing internal routine for output. Data will not be stored on the data set list.\n"); //if (circular_ || gnuplot_) { // mprintf("\tWarning: gnuplot and/or circular specified; advanced grace/gnuplot\n"); // mprintf("\t formatting disabled.\n");*/ if (circular_) mprintf("\tcircular: Output coordinates will be wrapped.\n"); if (gnuplot_ && outfile_ == 0) mprintf("\tgnuplot: Output will be in gnuplot-readable format.\n"); //} if (normalize_ == NORM_SUM) mprintf("\tnorm: Sum over bins will be normalized to 1.0.\n"); else if (normalize_ == NORM_INT) mprintf("\tnormint: Integral over bins will be normalized to 1.0.\n"); if (!traj3dName_.empty()) { mprintf("\tPseudo-trajectory will be written to '%s' with format %s\n", traj3dName_.c_str(), TrajectoryFile::FormatString(traj3dFmt_)); if (!parmoutName_.empty()) mprintf("\tCorresponding pseudo-topology will be written to '%s'\n", parmoutName_.c_str()); } return Analysis::OK; }
Analysis::RetType Analysis_Spline::Setup(ArgList& analyzeArgs, DataSetList* datasetlist, DataFileList* DFLin, int debugIn) { std::string setname = analyzeArgs.GetStringKey("name"); outfile_ = DFLin->AddDataFile(analyzeArgs.GetStringKey("out"), analyzeArgs); meshsize_ = analyzeArgs.getKeyInt("meshsize", 0); meshfactor_ = -1.0; if (meshsize_ < 3) { meshfactor_ = analyzeArgs.getKeyDouble("meshfactor", -1.0); if (meshfactor_ < Constants::SMALL) { mprinterr("Error: Either meshsize must be specified and > 2, or meshfactor must be\n" "Error: specified and > 0.0\n"); return Analysis::ERR; } } if (analyzeArgs.Contains("meshmin")) { meshmin_ = analyzeArgs.getKeyDouble("meshmin", 0.0); useDefaultMin_ = true; } else useDefaultMin_ = false; if (analyzeArgs.Contains("meshmax")) { meshmax_ = analyzeArgs.getKeyDouble("meshmax", -1.0); useDefaultMax_ = true; } else useDefaultMax_ = false; if (useDefaultMin_ && useDefaultMax_ && meshmax_ < meshmin_) { mprinterr("Error: meshmax must be > meshmin\n"); return Analysis::ERR; } // Select datasets from remaining args if (input_dsets_.AddSetsFromArgs( analyzeArgs.RemainingArgs(), *datasetlist )) { mprinterr("Error: Could not add data sets.\n"); return Analysis::ERR; } if (input_dsets_.empty()) { mprinterr("Error: No input data sets.\n"); return Analysis::ERR; } // Set up output datasets Dimension Xdim( meshmin_, (meshmax_ - meshmin_) / (double)meshsize_ ); for (Array1D::const_iterator dsIn = input_dsets_.begin(); dsIn != input_dsets_.end(); ++dsIn) { DataSet* ds = datasetlist->AddSet(DataSet::XYMESH, setname, "Spline"); if (ds == 0) return Analysis::ERR; ds->SetLegend( "Spline(" + (*dsIn)->Meta().Legend() + ")" ); // TODO: Set individually based on input_dsets_ ds->SetDim(Dimension::X, Xdim); if (outfile_ != 0) outfile_->AddDataSet( ds ); output_dsets_.push_back( (DataSet_Mesh*)ds ); } mprintf(" SPLINE: Applying cubic splining to %u data sets\n", input_dsets_.size()); if (meshfactor_ < 0) mprintf("\tMesh size= %i\n", meshsize_); else mprintf("\tMesh size will be input set size multiplied by %f\n", meshfactor_); if (useDefaultMin_) mprintf("\tMesh min= %f,", meshmin_); else mprintf("\tMesh min will be input set min,"); if (useDefaultMax_) mprintf(" Mesh max= %f\n", meshmax_); else mprintf(" Mesh max will be input set max.\n"); if (outfile_ != 0) { if (!setname.empty()) mprintf("\tOutput set name: %s\n", setname.c_str()); mprintf("\tOutfile name: %s\n", outfile_->DataFilename().base()); } //for (Array1D::const_iterator set = input_dsets_.begin(); set != input_dsets_.end(); ++set) // mprintf("\t%s\n", (*set)->legend()); return Analysis::OK; }
// Analysis_KDE::Setup() Analysis::RetType Analysis_KDE::Setup(ArgList& analyzeArgs, AnalysisSetup& setup, int debugIn) { if (analyzeArgs.Contains("min")) { default_min_ = analyzeArgs.getKeyDouble("min", 0.0); minArgSet_ = true; } if (analyzeArgs.Contains("max")) { default_max_ = analyzeArgs.getKeyDouble("max", 0.0); maxArgSet_ = true; } default_step_ = analyzeArgs.getKeyDouble("step", 0.0); default_bins_ = analyzeArgs.getKeyInt("bins", -1); if (default_step_ == 0.0 && default_bins_ < 1) { mprinterr("Error: Must set either bins or step.\n"); return Analysis::ERR; } Temp_ = analyzeArgs.getKeyDouble("free",-1.0); if (Temp_!=-1.0) calcFreeE_ = true; else calcFreeE_ = false; std::string setname = analyzeArgs.GetStringKey("name"); bandwidth_ = analyzeArgs.getKeyDouble("bandwidth", -1.0); DataFile* outfile = setup.DFL().AddDataFile( analyzeArgs.GetStringKey("out"), analyzeArgs ); DataFile* klOutfile = 0; // Get second data set for KL divergence calc. std::string q_dsname = analyzeArgs.GetStringKey("kldiv"); if (!q_dsname.empty()) { q_data_ = setup.DSL().GetDataSet( q_dsname ); if (q_data_ == 0) { mprinterr("Error: Data set %s not found.\n", q_dsname.c_str()); return Analysis::ERR; } if (q_data_->Ndim() != 1) { mprinterr("Error: Only 1D data sets supported.\n"); return Analysis::ERR; } klOutfile = setup.DFL().AddDataFile( analyzeArgs.GetStringKey("klout"), analyzeArgs ); } else { q_data_ = 0; kldiv_ = 0; } // Get AMD boost data set std::string amdname = analyzeArgs.GetStringKey("amd"); if (!amdname.empty()) { amddata_ = setup.DSL().GetDataSet( amdname ); if (amddata_ == 0) { mprinterr("Error: AMD data set %s not found.\n", amdname.c_str()); return Analysis::ERR; } if (amddata_->Ndim() != 1) { mprinterr("Error: AMD data set must be 1D.\n"); return Analysis::ERR; } } else amddata_ = 0; // Get data set data_ = setup.DSL().GetDataSet( analyzeArgs.GetStringNext() ); if (data_ == 0) { mprinterr("Error: No data set or invalid data set name specified\n"); return Analysis::ERR; } if (data_->Ndim() != 1) { mprinterr("Error: Only 1D data sets supported.\n"); return Analysis::ERR; } // Output data set output_ = setup.DSL().AddSet(DataSet::DOUBLE, setname, "kde"); if (output_ == 0) return Analysis::ERR; if (outfile != 0) outfile->AddDataSet( output_ ); // Output for KL divergence calc. if ( q_data_ != 0 ) { kldiv_ = setup.DSL().AddSet(DataSet::DOUBLE, MetaData(output_->Meta().Name(), "kld")); if (klOutfile != 0) klOutfile->AddDataSet( kldiv_ ); } mprintf(" KDE: Using gaussian KDE to histogram set \"%s\"\n", data_->legend()); if (amddata_!=0) mprintf("\tPopulating bins using AMD boost from data set %s\n", amddata_->legend()); if (q_data_ != 0) { mprintf("\tCalculating Kullback-Leibler divergence with set \"%s\"\n", q_data_->legend()); } if (bandwidth_ < 0.0) mprintf("\tBandwidth will be estimated.\n"); else mprintf("\tBandwidth= %f\n", bandwidth_); if (calcFreeE_) mprintf("\tFree energy in kcal/mol will be calculated from bin populations at %f K.\n",Temp_); return Analysis::OK; }
// Exec_RotateDihedral::Execute() Exec::RetType Exec_RotateDihedral::Execute(CpptrajState& State, ArgList& argIn) { // Get input COORDS set std::string setname = argIn.GetStringKey("crdset"); if (setname.empty()) { mprinterr("Error: Specify COORDS dataset name with 'crdset'.\n"); return CpptrajState::ERR; } DataSet_Coords* CRD = (DataSet_Coords*)State.DSL().FindCoordsSet( setname ); if (CRD == 0) { mprinterr("Error: Could not find COORDS set '%s'\n", setname.c_str()); return CpptrajState::ERR; } if (CRD->Size() < 1) { mprinterr("Error: COORDS set is empty.\n"); return CpptrajState::ERR; } int frame = argIn.getKeyInt("frame", 0); if (frame < 0 || frame >= (int)CRD->Size()) { mprinterr("Error: Specified frame %i is out of range.\n", frame+1); return CpptrajState::ERR; } mprintf(" ROTATEDIHEDRAL: Using COORDS '%s', frame %i\n", CRD->legend(), frame+1); // Get target frame Frame FRM = CRD->AllocateFrame(); CRD->GetFrame(frame, FRM); // Save as reference Frame refFrame = FRM; // Create output COORDS set if necessary DataSet_Coords* OUT = 0; int outframe = 0; std::string outname = argIn.GetStringKey("name"); if (outname.empty()) { // This will not work for TRAJ data sets if (CRD->Type() == DataSet::TRAJ) { mprinterr("Error: Using TRAJ as input set requires use of 'name' keyword for output.\n"); return CpptrajState::ERR; } OUT = CRD; outframe = frame; } else { // Create new output set with 1 empty frame. OUT = (DataSet_Coords*)State.DSL().AddSet( DataSet::COORDS, outname ); if (OUT == 0) return CpptrajState::ERR; OUT->Allocate( DataSet::SizeArray(1, 1) ); OUT->CoordsSetup( CRD->Top(), CRD->CoordsInfo() ); OUT->AddFrame( CRD->AllocateFrame() ); mprintf("\tOutput to set '%s'\n", OUT->legend()); } // Determine whether we are setting or incrementing. enum ModeType { SET = 0, INCREMENT }; ModeType mode = SET; if (argIn.Contains("value")) mode = SET; else if (argIn.Contains("increment")) mode = INCREMENT; else { mprinterr("Error: Specify 'value <value>' or 'increment <increment>'\n"); return CpptrajState::ERR; } double value = argIn.getKeyDouble(ModeStr[mode], 0.0); switch (mode) { case SET: mprintf("\tDihedral will be set to %g degrees.\n", value); break; case INCREMENT: mprintf("\tDihedral will be incremented by %g degrees.\n", value); break; } // Convert to radians value *= Constants::DEGRAD; // Select dihedral atoms int A1, A2, A3, A4; if (argIn.Contains("type")) { // By type ArgList typeArg = argIn.GetStringKey("type"); if (typeArg.empty()) { mprinterr("Error: No dihedral type specified after 'type'\n"); return CpptrajState::ERR; } DihedralSearch dihSearch; dihSearch.SearchForArgs( typeArg ); if (dihSearch.NoDihedralTokens()) { mprinterr("Error: Specified dihedral type not recognized.\n"); return CpptrajState::ERR; } // Get residue int res = argIn.getKeyInt("res", -1); if (res <= 0) { mprinterr("Error: If 'type' specified 'res' must be specified and > 0.\n"); return CpptrajState::ERR; } // Search for dihedrals. User residue #s start from 1. if (dihSearch.FindDihedrals(CRD->Top(), Range(res-1))) return CpptrajState::ERR; DihedralSearch::mask_it dih = dihSearch.begin(); A1 = dih->A0(); A2 = dih->A1(); A3 = dih->A2(); A4 = dih->A3(); } else { // By masks AtomMask m1( argIn.GetMaskNext() ); AtomMask m2( argIn.GetMaskNext() ); AtomMask m3( argIn.GetMaskNext() ); AtomMask m4( argIn.GetMaskNext() ); if (CRD->Top().SetupIntegerMask( m1 )) return CpptrajState::ERR; if (CRD->Top().SetupIntegerMask( m2 )) return CpptrajState::ERR; if (CRD->Top().SetupIntegerMask( m3 )) return CpptrajState::ERR; if (CRD->Top().SetupIntegerMask( m4 )) return CpptrajState::ERR; if (m1.Nselected() != 1) return MaskError( m1 ); if (m2.Nselected() != 1) return MaskError( m2 ); if (m3.Nselected() != 1) return MaskError( m3 ); if (m4.Nselected() != 1) return MaskError( m4 ); A1 = m1[0]; A2 = m2[0]; A3 = m3[0]; A4 = m4[0]; } mprintf("\tRotating dihedral defined by atoms '%s'-'%s'-'%s'-'%s'\n", CRD->Top().AtomMaskName(A1).c_str(), CRD->Top().AtomMaskName(A2).c_str(), CRD->Top().AtomMaskName(A3).c_str(), CRD->Top().AtomMaskName(A4).c_str()); // Set mask of atoms that will move during dihedral rotation AtomMask Rmask = DihedralSearch::MovingAtoms(CRD->Top(), A2, A3); // Calculate current value of dihedral double torsion = Torsion( FRM.XYZ(A1), FRM.XYZ(A2), FRM.XYZ(A3), FRM.XYZ(A4) ); // Calculate delta needed to get to target value. double delta; switch (mode) { case SET: delta = value - torsion; break; case INCREMENT: delta = value; break; } mprintf("\tOriginal torsion is %g, rotating by %g degrees.\n", torsion*Constants::RADDEG, delta*Constants::RADDEG); // Set axis of rotation Vec3 axisOfRotation = FRM.SetAxisOfRotation( A2, A3 ); // Calculate rotation matrix for delta. Matrix_3x3 rotationMatrix; rotationMatrix.CalcRotationMatrix(axisOfRotation, delta); // Rotate around axis FRM.Rotate(rotationMatrix, Rmask); // RMS-fit the non-moving part of the coords back on original AtomMask refMask = Rmask; refMask.InvertMask(); FRM.Align( refFrame, refMask ); // Update coords OUT->SetCRD( outframe, FRM ); return CpptrajState::OK; }
// Analysis_Modes::Setup() Analysis::RetType Analysis_Modes::Setup(ArgList& analyzeArgs, AnalysisSetup& setup, int debugIn) { debug_ = debugIn; // Analysis type if (analyzeArgs.hasKey("fluct")) type_ = FLUCT; else if (analyzeArgs.hasKey("displ")) type_ = DISPLACE; else if (analyzeArgs.hasKey("corr")) type_ = CORR; else if (analyzeArgs.Contains("trajout")) type_ = TRAJ; else if (analyzeArgs.hasKey("eigenval")) type_ = EIGENVAL; else if (analyzeArgs.hasKey("rmsip")) type_ = RMSIP; else { mprinterr("Error: No analysis type specified.\n"); return Analysis::ERR; } // Get modes name std::string modesfile = analyzeArgs.GetStringKey("name"); if (modesfile.empty()) { // Check for deprecated args CheckDeprecated(analyzeArgs, modesfile, "file"); CheckDeprecated(analyzeArgs, modesfile, "stack"); if (modesfile.empty()) { mprinterr("Error: No 'name <modes data set name>' argument given.\n"); return Analysis::ERR; } } // Get second modes name for RMSIP std::string modesfile2 = analyzeArgs.GetStringKey("name2"); if (type_ == RMSIP) { if (modesfile2.empty()) { mprinterr("Error: 'rmsip' requires second modes data 'name2 <modes>'\n"); return Analysis::ERR; } } else modesfile2.clear(); // Get topology for TRAJ/CORR Topology* analyzeParm = setup.DSL().GetTopology( analyzeArgs ); if (type_ == TRAJ ) { // Get trajectory format args for projected traj beg_ = analyzeArgs.getKeyInt("beg",1) - 1; // Args start at 1 std::string tOutName = analyzeArgs.GetStringKey("trajout"); if (tOutName.empty()) { mprinterr("Error: Require output trajectory filename, 'trajout <name>'\n"); return Analysis::ERR; } TrajectoryFile::TrajFormatType tOutFmt = TrajectoryFile::UNKNOWN_TRAJ; if ( analyzeArgs.Contains("trajoutfmt") ) tOutFmt = TrajectoryFile::GetFormatFromString( analyzeArgs.GetStringKey("trajoutfmt") ); if (analyzeParm == 0) { mprinterr("Error: Could not get topology for output trajectory.\n"); return Analysis::ERR; } AtomMask tOutMask( analyzeArgs.GetStringKey("trajoutmask") ); if ( analyzeParm->SetupIntegerMask( tOutMask ) || tOutMask.None() ) { mprinterr("Error: Could not setup output trajectory mask.\n"); return Analysis::ERR; } tOutMask.MaskInfo(); // Strip topology to match mask. if (tOutParm_ != 0) delete tOutParm_; tOutParm_ = analyzeParm->modifyStateByMask( tOutMask ); if (tOutParm_ == 0) { mprinterr("Error: Could not create topology to match mask.\n"); return Analysis::ERR; } // Setup output traj if (trajout_.InitTrajWrite( tOutName, ArgList(), tOutFmt ) != 0) { mprinterr("Error: Could not init output trajectory.\n"); return Analysis::ERR; } // Get min and max for PC pcmin_ = analyzeArgs.getKeyDouble("pcmin", -10.0); pcmax_ = analyzeArgs.getKeyDouble("pcmax", 10.0); if (pcmax_ < pcmin_ || pcmax_ - pcmin_ < Constants::SMALL) { mprinterr("Error: pcmin must be less than pcmax\n"); return Analysis::ERR; } tMode_ = analyzeArgs.getKeyInt("tmode", 1); } else { // Args for everything else beg_ = analyzeArgs.getKeyInt("beg",7) - 1; // Args start at 1 bose_ = analyzeArgs.hasKey("bose"); calcAll_ = analyzeArgs.hasKey("calcall"); } end_ = analyzeArgs.getKeyInt("end", 50); factor_ = analyzeArgs.getKeyDouble("factor",1.0); std::string setname = analyzeArgs.GetStringKey("setname"); // Check if modes name exists on the stack modinfo_ = (DataSet_Modes*)setup.DSL().FindSetOfType( modesfile, DataSet::MODES ); if (modinfo_ == 0) { mprinterr("Error: '%s' not found: %s\n", modesfile.c_str(), DataSet_Modes::DeprecateFileMsg); return Analysis::ERR; } if (!modesfile2.empty()) { modinfo2_ = (DataSet_Modes*)setup.DSL().FindSetOfType( modesfile2, DataSet::MODES ); if (modinfo2_ == 0) { mprinterr("Error: Set %s not found.\n", modesfile2.c_str()); return Analysis::ERR; } } // Check modes type for specified analysis if (type_ == FLUCT || type_ == DISPLACE || type_ == CORR || type_ == TRAJ) { if (modinfo_->Meta().ScalarType() != MetaData::COVAR && modinfo_->Meta().ScalarType() != MetaData::MWCOVAR) { mprinterr("Error: Modes must be of type COVAR or MWCOVAR for %s.\n", analysisTypeString[type_]); return Analysis::ERR; } } // Get output filename for types that use DataSets std::string outfilename = analyzeArgs.GetStringKey("out"); // TODO all datafile? DataFile* dataout = 0; if (type_ == FLUCT || type_ == DISPLACE || type_ == EIGENVAL || type_ == RMSIP) dataout = setup.DFL().AddDataFile( outfilename, analyzeArgs ); else if (type_ == CORR) { // CORR-specific setup outfile_ = setup.DFL().AddCpptrajFile( outfilename, "Modes analysis", DataFileList::TEXT, true ); if (outfile_ == 0) return Analysis::ERR; // Get list of atom pairs if (analyzeParm == 0) { mprinterr("Error: 'corr' requires topology.\n"); return Analysis::ERR; } std::string maskexp = analyzeArgs.GetStringKey("mask1"); if (maskexp.empty()) { while (analyzeArgs.hasKey("maskp")) { // Next two arguments should be one-atom masks std::string a1mask = analyzeArgs.GetMaskNext(); std::string a2mask = analyzeArgs.GetMaskNext(); if (a1mask.empty() || a2mask.empty()) { mprinterr("Error: For 'corr' two 1-atom masks are expected.\n"); return Analysis::ERR; } // Check that each mask is just 1 atom AtomMask m1( a1mask ); AtomMask m2( a2mask ); analyzeParm->SetupIntegerMask( m1 ); analyzeParm->SetupIntegerMask( m2 ); if ( m1.Nselected()==1 && m2.Nselected()==1 ) // Store atom pair atompairStack_.push_back( std::pair<int,int>( m1[0], m2[0] ) ); else { mprinterr("Error: For 'corr', masks should specify only one atom.\n" "\tM1[%s]=%i atoms, M2[%s]=%i atoms.\n", m1.MaskString(), m1.Nselected(), m2.MaskString(), m2.Nselected()); return Analysis::ERR; } } } else { AtomMask mask1( maskexp ); maskexp = analyzeArgs.GetStringKey("mask2"); if (maskexp.empty()) { mprinterr("Error: 'mask2' must be specified if 'mask1' is.\n"); return Analysis::ERR; } AtomMask mask2( maskexp ); if ( analyzeParm->SetupIntegerMask( mask1 ) ) return Analysis::ERR; if ( analyzeParm->SetupIntegerMask( mask2 ) ) return Analysis::ERR; mask1.MaskInfo(); mask2.MaskInfo(); if (mask1.None() || mask2.None()) { mprinterr("Error: One or both masks are empty.\n"); return Analysis::ERR; } if (mask1.Nselected() != mask2.Nselected()) { mprinterr("Error: # atoms in mask 1 not equal to # atoms in mask 2.\n"); return Analysis::ERR; } for (int idx = 0; idx != mask1.Nselected(); idx++) atompairStack_.push_back( std::pair<int,int>( mask1[idx], mask2[idx] ) ); } if ( atompairStack_.empty() ) { mprinterr("Error: No atom pairs found (use 'maskp' or 'mask1'/'mask2' keywords.)\n"); return Analysis::ERR; } } // Set up data sets Dimension Xdim; if (type_ == FLUCT) { if (setname.empty()) setname = setup.DSL().GenerateDefaultName("FLUCT"); MetaData md(setname, "rmsX"); OutSets_.resize( 4, 0 ); OutSets_[RMSX] = setup.DSL().AddSet( DataSet::DOUBLE, md ); md.SetAspect("rmsY"); OutSets_[RMSY] = setup.DSL().AddSet( DataSet::DOUBLE, md ); md.SetAspect("rmsZ"); OutSets_[RMSZ] = setup.DSL().AddSet( DataSet::DOUBLE, md ); md.SetAspect("rms"); OutSets_[RMS] = setup.DSL().AddSet( DataSet::DOUBLE, md ); Xdim = Dimension(1, 1, "Atom_no."); } else if (type_ == DISPLACE) { if (setname.empty()) setname = setup.DSL().GenerateDefaultName("DISPL"); MetaData md(setname, "displX"); OutSets_.resize( 3, 0 ); OutSets_[RMSX] = setup.DSL().AddSet( DataSet::DOUBLE, md ); md.SetAspect("displY"); OutSets_[RMSY] = setup.DSL().AddSet( DataSet::DOUBLE, md ); md.SetAspect("displZ"); OutSets_[RMSZ] = setup.DSL().AddSet( DataSet::DOUBLE, md ); Xdim = Dimension(1, 1, "Atom_no."); } else if (type_ == EIGENVAL) { if (setname.empty()) setname = setup.DSL().GenerateDefaultName("XEVAL"); MetaData md(setname, "Frac"); OutSets_.resize( 3, 0 ); OutSets_[0] = setup.DSL().AddSet( DataSet::DOUBLE, md ); md.SetAspect("Cumulative"); OutSets_[1] = setup.DSL().AddSet( DataSet::DOUBLE, md ); md.SetAspect("Eigenval"); OutSets_[2] = setup.DSL().AddSet( DataSet::DOUBLE, md ); Xdim = Dimension( 1, 1, "Mode" ); } else if (type_ == RMSIP) { if (setname.empty()) setname = setup.DSL().GenerateDefaultName("RMSIP"); OutSets_.push_back( setup.DSL().AddSet( DataSet::DOUBLE, setname ) ); if (dataout != 0) dataout->ProcessArgs("noxcol"); OutSets_[0]->SetupFormat() = TextFormat(TextFormat::GDOUBLE); OutSets_[0]->SetLegend( modinfo_->Meta().Legend() + "_X_" + modinfo2_->Meta().Legend() ); } for (std::vector<DataSet*>::const_iterator set = OutSets_.begin(); set != OutSets_.end(); ++set) { if (*set == 0) return Analysis::ERR; if (dataout != 0) dataout->AddDataSet( *set ); (*set)->SetDim(Dimension::X, Xdim); } // Status mprintf(" ANALYZE MODES: Calculating %s using modes from %s", analysisTypeString[type_], modinfo_->legend()); if ( type_ != TRAJ ) { if (type_ != EIGENVAL) mprintf(", modes %i to %i", beg_+1, end_); if (outfile_ != 0) mprintf("\n\tResults are written to %s\n", outfile_->Filename().full()); else if (dataout != 0) mprintf("\n\tResults are written to '%s'\n", dataout->DataFilename().full()); if (type_ != EIGENVAL && type_ != RMSIP) { if (bose_) mprintf("\tBose statistics used.\n"); else mprintf("\tBoltzmann statistics used.\n"); if (calcAll_) mprintf("\tEigenvectors associated with zero or negative eigenvalues will be used.\n"); else mprintf("\tEigenvectors associated with zero or negative eigenvalues will be skipped.\n"); } if (type_ == DISPLACE) mprintf("\tFactor for displacement: %f\n", factor_); if (type_ == CORR) { mprintf("\tUsing the following atom pairs:"); for (modestack_it apair = atompairStack_.begin(); apair != atompairStack_.end(); ++apair) mprintf(" (%i,%i)", apair->first+1, apair->second+1 ); mprintf("\n"); } if (type_ == RMSIP) mprintf("\tRMSIP calculated to modes in %s\n", modinfo2_->legend()); } else { mprintf("\n\tCreating trajectory for mode %i\n" "\tWriting to trajectory %s\n" "\tPC range: %f to %f\n" "\tScaling factor: %f\n", tMode_, trajout_.Traj().Filename().full(), pcmin_, pcmax_, factor_); } return Analysis::OK; }
// Exec_DataSetCmd::ChangeDim() Exec::RetType Exec_DataSetCmd::ChangeDim(CpptrajState const& State, ArgList& argIn) { int ndim = -1; if (argIn.hasKey("xdim")) ndim = 0; else if (argIn.hasKey("ydim")) ndim = 1; else if (argIn.hasKey("zdim")) ndim = 2; else ndim = argIn.getKeyInt("ndim", -1); if (ndim < 0) { mprinterr("Error: Specify xdim/ydim/zdim or dimension number with ndim.\n"); return CpptrajState::ERR; } if (ndim < 3) { static const char DIMSTR[3] = { 'X', 'Y', 'Z' }; mprintf("\tChanging the following in the %c dimension:\n", DIMSTR[ndim]); } else mprintf("\tChanging the following in dimension %i\n", ndim); bool changeLabel, changeMin, changeStep; std::string label; double min = 0.0; double step = 0.0; if (argIn.Contains("label")) { label = argIn.GetStringKey("label"); changeLabel = true; mprintf("\tNew Label: %s\n", label.c_str()); } else changeLabel = false; if (argIn.Contains("step")) { step = argIn.getKeyDouble("step", 0.0); changeStep = true; mprintf("\tNew step: %g\n", step); } else changeStep = false; if (argIn.Contains("min")) { min = argIn.getKeyDouble("min", 0.0); changeMin = true; mprintf("\tNew min: %g\n", min); } else changeMin = false; // Loop over all DataSet arguments std::string ds_arg = argIn.GetStringNext(); while (!ds_arg.empty()) { DataSetList dsl = State.DSL().GetMultipleSets( ds_arg ); for (DataSetList::const_iterator ds = dsl.begin(); ds != dsl.end(); ++ds) { if (ndim < (int)(*ds)->Ndim()) { mprintf("\t%s\n", (*ds)->legend()); Dimension dim = (*ds)->Dim(ndim); if (changeLabel) dim.SetLabel( label ); if (changeMin) dim.ChangeMin( min ); if (changeStep) dim.ChangeStep( step ); (*ds)->SetDim(ndim, dim); } else mprintf("Warning: Set '%s' has fewer then %i dimensions - skipping.\n", (*ds)->legend(), ndim); } ds_arg = argIn.GetStringNext(); } return CpptrajState::OK; }
// Exec_DataSetCmd::Remove() Exec::RetType Exec_DataSetCmd::Remove(CpptrajState& State, ArgList& argIn) { std::string status; // Get criterion type CriterionType criterion = UNKNOWN_C; for (int i = 1; i < (int)N_C; i++) if (argIn.hasKey( CriterionKeys[i] )) { criterion = (CriterionType)i; status.assign( CriterionKeys[i] ); break; } if (criterion == UNKNOWN_C) { mprinterr("Error: No criterion specified for 'remove'.\n"); return CpptrajState::ERR; } // Get select type SelectType select = UNKNOWN_S; std::string val1, val2; for (const SelectPairType* ptr = SelectKeys; ptr->key_ != 0; ptr++) if (argIn.Contains( ptr->key_ )) { select = ptr->type_; val1 = argIn.GetStringKey( ptr->key_ ); status.append( " " + std::string(ptr->key_) + " " + val1 ); // Get 'and' value for between/outside. TODO put nargs in SelectPairType? if (select == BETWEEN || select == OUTSIDE) { val2 = argIn.GetStringKey("and"); if (val2.empty()) { mprinterr("Error: Missing 'and' value for selection '%s'\n", ptr->key_); return CpptrajState::ERR; } status.append(" and " + val2); } break; } if (select == UNKNOWN_S || val1.empty()) { mprinterr("Error: No selection specified for 'remove'.\n"); return CpptrajState::ERR; } if ( (criterion == SMODE || criterion == STYPE) && (select != EQUAL && select != NOT_EQUAL) ) { mprinterr("Error: Specified select not valid for criterion '%s'\n", CriterionKeys[criterion]); return CpptrajState::ERR; } mprintf("\tRemoving data sets"); std::string setSelectArg = argIn.GetStringNext(); if (setSelectArg.empty()) setSelectArg.assign("*"); else mprintf(" within selection '%s'", setSelectArg.c_str()); mprintf(" %s\n", status.c_str()); DataSetList tempDSL = State.DSL().GetMultipleSets( setSelectArg ); if (tempDSL.empty()) { mprinterr("Error: No data sets selected.\n"); return CpptrajState::ERR; } // Remove sets unsigned int Nremoved = 0; if ( criterion == AVERAGE ) { if (!validDouble( val1 )) { mprinterr("Error: '%s' is not a valid number\n", val1.c_str()); return CpptrajState::ERR; } double d_val1 = convertToDouble( val1 ); double d_val2 = d_val1; if (!val2.empty()) { if (!validDouble( val2 )) { mprinterr("Error: '%s' is not a valid number\n", val2.c_str()); return CpptrajState::ERR; } d_val2 = convertToDouble( val2 ); } for (DataSetList::const_iterator ds = tempDSL.begin(); ds != tempDSL.end(); ++ds) { if ( (*ds)->Group() != DataSet::SCALAR_1D ) mprintf("Warning: '%s' is not a valid data set for 'average' criterion.\n", (*ds)->legend()); else { DataSet_1D const& ds1 = static_cast<DataSet_1D const&>( *(*ds) ); double avg = ds1.Avg(); bool remove = false; switch (select) { case EQUAL : remove = (avg == d_val1); break; case NOT_EQUAL : remove = (avg != d_val1); break; case LESS_THAN : remove = (avg < d_val1); break; case GREATER_THAN : remove = (avg > d_val1); break; case BETWEEN : remove = (avg > d_val1 && avg < d_val2); break; case OUTSIDE : remove = (avg < d_val1 || avg > d_val2); break; case UNKNOWN_S: case N_S : return CpptrajState::ERR; // Sanity check } if (remove) { mprintf("\t Removing set '%s' (avg is %g)\n", (*ds)->legend(), avg); State.RemoveDataSet( *ds ); ++Nremoved; } } } } else if ( criterion == SIZE ) { if (!validInteger( val1 )) { mprinterr("Error: '%s' is not a valid number\n", val1.c_str()); return CpptrajState::ERR; } unsigned int i_val1 = (unsigned int)convertToInteger( val1 ); unsigned int i_val2 = i_val1; if (!val2.empty()) { if (!validInteger( val2 )) { mprinterr("Error: '%s' is not a valid number\n", val2.c_str()); return CpptrajState::ERR; } i_val2 = convertToInteger( val2 ); } for (DataSetList::const_iterator ds = tempDSL.begin(); ds != tempDSL.end(); ++ds) { unsigned int size = (*ds)->Size(); bool remove = false; switch ( select ) { case EQUAL : remove = (size == i_val1); break; case NOT_EQUAL : remove = (size != i_val1); break; case LESS_THAN : remove = (size < i_val1); break; case GREATER_THAN : remove = (size > i_val1); break; case BETWEEN : remove = (size > i_val1 && size < i_val2); break; case OUTSIDE : remove = (size < i_val1 || size > i_val2); break; case UNKNOWN_S: case N_S : return CpptrajState::ERR; // Sanity check } if (remove) { mprintf("\t Removing set '%s' (size is %u)\n", (*ds)->legend(), size); State.RemoveDataSet( *ds ); ++Nremoved; } } } else if ( criterion == SMODE ) { MetaData::scalarMode mode_val = MetaData::ModeFromKeyword( val1 ); if (mode_val == MetaData::UNKNOWN_MODE) { mprinterr("Error: '%s' is not a valid mode.\n", val1.c_str()); return CpptrajState::ERR; } for (DataSetList::const_iterator ds = tempDSL.begin(); ds != tempDSL.end(); ++ds) { bool remove = false; MetaData::scalarMode mode = (*ds)->Meta().ScalarMode(); if (select == EQUAL ) remove = ( mode == mode_val ); else if (select == NOT_EQUAL) remove = ( mode != mode_val ); else return CpptrajState::ERR; // Sanity check if (remove) { mprintf("\t Removing set '%s' (mode is '%s')\n", (*ds)->legend(), MetaData::ModeString(mode)); State.RemoveDataSet( *ds ); ++Nremoved; } } } else if ( criterion == STYPE ) { MetaData::scalarType type_val = MetaData::TypeFromKeyword( val1, MetaData::UNKNOWN_MODE ); if (type_val == MetaData::UNDEFINED) { mprinterr("Error: '%s' is not a valid type.\n", val1.c_str()); return CpptrajState::ERR; } for (DataSetList::const_iterator ds = tempDSL.begin(); ds != tempDSL.end(); ++ds) { bool remove = false; MetaData::scalarType type = (*ds)->Meta().ScalarType(); if (select == EQUAL ) remove = ( type == type_val ); else if (select == NOT_EQUAL) remove = ( type != type_val ); else return CpptrajState::ERR; // Sanity check if (remove) { mprintf("\t Removing set '%s' (typeis '%s')\n", (*ds)->legend(), MetaData::TypeString(type)); State.RemoveDataSet( *ds ); ++Nremoved; } } } else { mprinterr("Internal Error: Criterion not yet implemented.\n"); return CpptrajState::ERR; } mprintf("\tRemoved %u of %zu sets.\n", Nremoved, tempDSL.size()); return CpptrajState::OK; }