EMAN::RT3DGridAligner Class Reference
[a function or class that is CUDA enabled]

rotational and translational alignment using a square qrid of Altitude and Azimuth values (the phi range is specifiable) This aligner is ported from the original tomohunter.py - it is less efficient than searching on the sphere (RT3DSphereAligner). More...

#include <aligner.h>

Inheritance diagram for EMAN::RT3DGridAligner:

Inheritance graph
[legend]
Collaboration diagram for EMAN::RT3DGridAligner:

Collaboration graph
[legend]
List of all members.

Public Member Functions

virtual EMDataalign (EMData *this_img, EMData *to_img, const string &cmp_name="ccc.tomo", const Dict &cmp_params=Dict()) const
 See Aligner comments for more details.
virtual EMDataalign (EMData *this_img, EMData *to_img) const
 See Aligner comments for more details.
virtual vector< Dictxform_align_nbest (EMData *this_img, EMData *to_img, const unsigned int nsoln, const string &cmp_name, const Dict &cmp_params) const
 See Aligner comments for more details.
virtual string get_name () const
 Get the Aligner's name.
virtual string get_desc () const
virtual TypeDict get_param_types () const

Static Public Member Functions

static AlignerNEW ()

Static Public Attributes

static const string NAME = "rotate_translate_3d_grid"

Detailed Description

rotational and translational alignment using a square qrid of Altitude and Azimuth values (the phi range is specifiable) This aligner is ported from the original tomohunter.py - it is less efficient than searching on the sphere (RT3DSphereAligner).

This is for use as a course aligner. For refineing alignments, use the refine_3d_grid aligner. In general this aligner is not used much and is mostly depreciated.

Parameters:
daz The angle increment in the azimuth direction
laz Lower bound for the azimuth direction
uaz Upper bound for the azimuth direction
dphi The angle increment in the phi direction
lphi Lower bound for the phi direction
uphi Upper bound for the phi direction
dalt The angle increment in the altitude direction
lalt Lower bound for the altitude direction
ualt Upper bound for the altitude direction
dotrans Do a translational search
search The maximum length of the detectable translational shift - if you supply this parameter you can not supply the maxshiftx, maxshifty or maxshiftz parameters. Each approach is mutually exclusive
searchx The maximum length of the detectable translational shift in the x direction- if you supply this parameter you can not supply the maxshift parameters
searchy The maximum length of the detectable translational shift in the y direction- if you supply this parameter you can not supply the maxshift parameters
searchz The maximum length of the detectable translational shift in the z direction- if you supply this parameter you can not supply the maxshift parameters
verbose Turn this on to have useful information printed to standard out
Author:
John Flanagan and David Woolford (ported from Mike Schmid's e2tomohuntThis is the increment applied to the inplane rotationer code - Mike Schmid is the intellectual author)
Date:
Feb 2011

Definition at line 1518 of file aligner.h.


Member Function Documentation

virtual EMData* EMAN::RT3DGridAligner::align ( EMData this_img,
EMData to_img 
) const [inline, virtual]

See Aligner comments for more details.

Implements EMAN::Aligner.

Definition at line 1527 of file aligner.h.

References align().

01528                         {
01529                                 return align(this_img, to_img, "ccc.tomo", Dict());
01530                         }

EMData * RT3DGridAligner::align ( EMData this_img,
EMData to_img,
const string &  cmp_name = "ccc.tomo",
const Dict cmp_params = Dict() 
) const [virtual]

See Aligner comments for more details.

Implements EMAN::Aligner.

Definition at line 2413 of file aligner.cpp.

References EMAN::EMData::process(), EMAN::EMData::set_attr(), t, and xform_align_nbest().

Referenced by align().

02414 {
02415 
02416         vector<Dict> alis = xform_align_nbest(this_img,to,1,cmp_name,cmp_params);
02417 
02418         Dict t;
02419         Transform* tr = (Transform*) alis[0]["xform.align3d"];
02420         t["transform"] = tr;
02421         EMData* soln = this_img->process("xform",t);
02422         soln->set_attr("xform.align3d",tr);
02423         delete tr; tr = 0;
02424 
02425         return soln;
02426 
02427 }

virtual string EMAN::RT3DGridAligner::get_desc (  )  const [inline, virtual]

Implements EMAN::Aligner.

Definition at line 1542 of file aligner.h.

01543                         {
01544                                 return "3D rotational and translational alignment using specified ranges and maximum shifts";
01545                         }

virtual string EMAN::RT3DGridAligner::get_name (  )  const [inline, virtual]

Get the Aligner's name.

Each Aligner is identified by a unique name.

Returns:
The Aligner's name.

Implements EMAN::Aligner.

Definition at line 1537 of file aligner.h.

References NAME.

01538                         {
01539                                 return NAME;
01540                         }

virtual TypeDict EMAN::RT3DGridAligner::get_param_types (  )  const [inline, virtual]

Implements EMAN::Aligner.

Definition at line 1552 of file aligner.h.

References EMAN::EMObject::BOOL, EMAN::EMObject::FLOAT, EMAN::EMObject::INT, EMAN::TypeDict::put(), and EMAN::EMObject::TRANSFORM.

01553                         {
01554                                 TypeDict d;
01555                                 d.put("daz", EMObject::FLOAT,"The angle increment in the azimuth direction. Default is 10");
01556                                 d.put("az0", EMObject::FLOAT,"Lower bound for the azimuth direction. Default it 0");
01557                                 d.put("az1", EMObject::FLOAT,"Upper bound for the azimuth direction. Default it 180.0");
01558                                 d.put("dphi", EMObject::FLOAT,"The angle increment in the phi direction. Default is 10");
01559                                 d.put("phi0", EMObject::FLOAT,"Lower bound for the phi direction. Default it 0");
01560                                 d.put("phi1", EMObject::FLOAT,"Upper bound for the phi direction. Default it 360.0");
01561                                 d.put("dalt", EMObject::FLOAT,"The angle increment in the altitude direction. Default is 10");
01562                                 d.put("alt0", EMObject::FLOAT,"Lower bound for the altitude direction. Default it 0");
01563                                 d.put("alt1", EMObject::FLOAT,"Upper bound for the altitude direction. Default it 360.0");
01564                                 d.put("dotrans", EMObject::BOOL,"Do a translational search. Default is True(1)");
01565                                 d.put("search", EMObject::INT,"The maximum length of the detectable translational shift - if you supply this parameter you can not supply the maxshiftx, maxshifty or maxshiftz parameters. Each approach is mutually exclusive.");
01566                                 d.put("searchx", EMObject::INT,"The maximum length of the detectable translational shift in the x direction- if you supply this parameter you can not supply the maxshift parameters. Default is 3.");
01567                                 d.put("searchy", EMObject::INT,"The maximum length of the detectable translational shift in the y direction- if you supply this parameter you can not supply the maxshift parameters. Default is 3.");
01568                                 d.put("searchz", EMObject::INT,"The maximum length of the detectable translational shift in the z direction- if you supply this parameter you can not supply the maxshift parameters. Default is 3");
01569                                 d.put("initxform", EMObject::TRANSFORM,"The Transform storing the starting position. If unspecified the identity matrix is used");
01570                                 d.put("verbose", EMObject::BOOL,"Turn this on to have useful information printed to standard out.");
01571                                 return d;
01572                         }

static Aligner* EMAN::RT3DGridAligner::NEW (  )  [inline, static]

Definition at line 1547 of file aligner.h.

01548                         {
01549                                 return new RT3DGridAligner();
01550                         }

vector< Dict > RT3DGridAligner::xform_align_nbest ( EMData this_img,
EMData to_img,
const unsigned int  nsoln,
const string &  cmp_name,
const Dict cmp_params 
) const [virtual]

See Aligner comments for more details.

Reimplemented from EMAN::Aligner.

Definition at line 2429 of file aligner.cpp.

References EMAN::EMData::calc_ccf(), EMAN::EMData::calc_max_location_wrap(), calc_max_location_wrap_cuda(), EMAN::Cmp::cmp(), copy(), data, EMAN::EMData::do_fft(), EMAN::EMData::get_ndim(), get_stats_cuda(), EMAN::EMData::get_value_at_wrap(), EMAN::EMData::get_xsize(), EMAN::EMData::get_ysize(), EMAN::EMData::get_zsize(), EMAN::Dict::has_key(), ImageDimensionException, InvalidParameterException, EMAN::Aligner::params, phi, EMAN::EMData::process(), EMAN::EMData::process_inplace(), EMAN::Dict::set_default(), EMAN::Transform::set_trans(), sqrt(), and t.

Referenced by align().

02429                                                                                                                                                                {
02430 
02431         if ( this_img->get_ndim() != 3 || to->get_ndim() != 3 ) {
02432                 throw ImageDimensionException("This aligner only works for 3D images");
02433         }
02434 
02435         int searchx = 0;
02436         int searchy = 0;
02437         int searchz = 0;
02438         
02439         bool dotrans = params.set_default("dotrans",1);
02440         if (params.has_key("search")) {
02441                 vector<string> check;
02442                 check.push_back("searchx");
02443                 check.push_back("searchy");
02444                 check.push_back("searchz");
02445                 for(vector<string>::const_iterator cit = check.begin(); cit != check.end(); ++cit) {
02446                         if (params.has_key(*cit)) throw InvalidParameterException("The search parameter is mutually exclusive of the searchx, searchy, and searchz parameters");
02447                 }
02448                 int search  = params["search"];
02449                 searchx = search;
02450                 searchy = search;
02451                 searchz = search;
02452         } else {
02453                 searchx = params.set_default("searchx",3);
02454                 searchy = params.set_default("searchy",3);
02455                 searchz = params.set_default("searchz",3);
02456         }
02457         
02458         Transform* initxform;
02459         if (params.has_key("initxform") ) {
02460                 // Unlike the 2d refine aligner, this class doesn't require the starting transform's
02461                 // parameters to form the starting guess. Instead the Transform itself
02462                 // is perturbed carefully (using quaternion rotation) to overcome problems that arise
02463                 // when you use orthogonally-based Euler angles
02464                 initxform = params["initxform"];
02465         }else {
02466                 initxform = new Transform(); // is the identity
02467         }
02468         
02469         float lalt = params.set_default("alt0",0.0f);
02470         float laz = params.set_default("az0",0.0f);
02471         float lphi = params.set_default("phi0",0.0f);
02472         float ualt = params.set_default("alt1",180.0f); // I am using 179.9 rather than 180 to avoid resampling
02473         float uphi = params.set_default("phi1",360.0f); // I am using 359.9 rather than 180 to avoid resampling 0 = 360 (for perodic functions)
02474         float uaz = params.set_default("az1",360.0f);   // I am using 359.9 rather than 180 to avoid resampling 0 = 360 (for perodic functions)
02475         float dalt = params.set_default("dalt",10.f);
02476         float daz = params.set_default("daz",10.f);
02477         float dphi = params.set_default("dphi",10.f);
02478         bool verbose = params.set_default("verbose",false);
02479         
02480         //in case we arre aligning tomos
02481         Dict altered_cmp_params(cmp_params);
02482         if (cmp_name == "ccc.tomo") {
02483                 altered_cmp_params.set_default("searchx", searchx);
02484                 altered_cmp_params.set_default("searchy", searchy);
02485                 altered_cmp_params.set_default("searchz", searchz);
02486                 altered_cmp_params.set_default("norm", true);
02487         }
02488 
02489         vector<Dict> solns;
02490         if (nsoln == 0) return solns; // What was the user thinking?
02491         for (unsigned int i = 0; i < nsoln; ++i ) {
02492                 Dict d;
02493                 d["score"] = 1.e24;
02494                 Transform t; // identity by default
02495                 d["xform.align3d"] = &t; // deep copy is going on here
02496                 solns.push_back(d);
02497         }
02498         
02499         bool tomography = (cmp_name == "ccc.tomo") ? 1 : 0;
02500         EMData * tofft = 0;
02501         if(dotrans || tomography){
02502                 tofft = to->do_fft();
02503         }
02504         
02505 #ifdef EMAN2_USING_CUDA 
02506         if(EMData::usecuda == 1) {
02507                 if(!this_img->getcudarodata()) this_img->copy_to_cudaro();  // safer call
02508                 if(!to->getcudarwdata()) to->copy_to_cuda();
02509                 if(to->getcudarwdata()){if(tofft) tofft->copy_to_cuda();}
02510         }
02511 #endif
02512 
02513         Dict d;
02514         d["type"] = "eman"; // d is used in the loop below
02515         Transform trans = Transform();
02516         Cmp* c = Factory <Cmp>::get(cmp_name, cmp_params);
02517         bool use_cpu = true;
02518         for ( float alt = lalt; alt <= ualt; alt += dalt) {
02519                 // An optimization for the range of az is made at the top of the sphere
02520                 // If you think about it, this is just a coarse way of making this approach slightly more efficient
02521                 for ( float az = laz; az < uaz; az += daz ){
02522                         if (verbose) {
02523                                 cout << "Trying angle alt " << alt << " az " << az << endl;
02524                         }
02525                         for( float phi = lphi; phi < uphi; phi += dphi ) {
02526                                 d["alt"] = alt;
02527                                 d["phi"] = phi; 
02528                                 d["az"] = az;
02529                                 Transform t(d);
02530                                 t = t*(*initxform);
02531                                 EMData* transformed = this_img->process("xform",Dict("transform",&t));
02532                         
02533                                 //need to do things a bit diffrent if we want to compare two tomos
02534                                 float best_score = 0.0f;
02535                                 if(dotrans || tomography){
02536                                         EMData* ccf = transformed->calc_ccf(tofft);
02537 #ifdef EMAN2_USING_CUDA 
02538                                         if(EMData::usecuda == 1){
02539                                                 use_cpu = false;;
02540                                                 CudaPeakInfo* data = calc_max_location_wrap_cuda(ccf->getcudarwdata(), ccf->get_xsize(), ccf->get_ysize(), ccf->get_zsize(), searchx, searchy, searchz);
02541                                                 trans.set_trans((float)-data->px, (float)-data->py, (float)-data->pz);
02542                                                 t = trans*t;    //composite transfrom to reflect the fact that we have done a rotation first and THEN a transformation
02543                                                 if (tomography) {
02544                                                         float2 stats = get_stats_cuda(ccf->getcudarwdata(), ccf->get_xsize(), ccf->get_ysize(), ccf->get_zsize());
02545                                                         best_score = -(data->peak - stats.x)/sqrt(stats.y); // Normalize, this is better than calling the norm processor since we only need to normalize one point
02546                                                 } else {
02547                                                         best_score = -data->peak;
02548                                                 }
02549                                                 delete data;
02550                                         }
02551 #endif
02552                                         if(use_cpu){
02553                                                 if(tomography) ccf->process_inplace("normalize");       
02554                                                 IntPoint point = ccf->calc_max_location_wrap(searchx,searchy,searchz);
02555                                                 trans.set_trans((float)-point[0], (float)-point[1], (float)-point[2]);
02556                                                 t = trans*t;    //composite transfrom to reflect the fact that we have done a rotation first and THEN a transformation
02557                                                 best_score = -ccf->get_value_at_wrap(point[0], point[1], point[2]);
02558                                         }
02559                                         delete ccf; ccf =0;
02560                                         delete transformed; transformed = 0;
02561                                 }
02562 
02563                                 if(!tomography){
02564                                         if(!transformed) transformed = this_img->process("xform",Dict("transform",&t));
02565                                         best_score = c->cmp(to,transformed);
02566                                         delete transformed; transformed = 0;
02567                                 }
02568                                 
02569                                 unsigned int j = 0;
02570                                 for ( vector<Dict>::iterator it = solns.begin(); it != solns.end(); ++it, ++j ) {
02571                                         if ( (float)(*it)["score"] > best_score ) {  // Note greater than - EMAN2 preferes minimums as a matter of policy
02572                                                 vector<Dict>::reverse_iterator rit = solns.rbegin();
02573                                                 copy(rit+1,solns.rend()-j,rit);
02574                                                 Dict& d = (*it);
02575                                                 d["score"] = best_score;
02576                                                 d["xform.align3d"] = &t;
02577                                                 break;
02578                                         }
02579                                 }
02580                         }
02581                 }
02582         }
02583         
02584         if(tofft) {delete tofft; tofft = 0;}
02585         if (c != 0) delete c;
02586         
02587         return solns;
02588 
02589 }


Member Data Documentation

const string RT3DGridAligner::NAME = "rotate_translate_3d_grid" [static]

Definition at line 1574 of file aligner.h.

Referenced by get_name().


The documentation for this class was generated from the following files:
Generated on Fri Aug 10 16:34:49 2012 for EMAN2 by  doxygen 1.4.7