View Javadoc

1   package org.lcsim.recon.tracking.seedtracker;
2   
3   import java.util.ArrayList;
4   import java.util.HashMap;
5   import java.util.List;
6   import java.util.Map;
7   import org.lcsim.constants.Constants;
8   import org.lcsim.fit.helicaltrack.HelicalTrackHit;
9   import org.lcsim.geometry.subdetector.BarrelEndcapFlag;
10  
11  /**
12   *
13   * @author Richard Partridge
14   */
15  public class SectorManager {
16  
17      private List<Sector> _sectorlist;
18      private Map<String, Sector> _sectormap;
19      private Map<String, List<Sector>> _slistmap;
20      private int _nphi;
21      private double _dphi;
22      private double _dz;
23      private int _nphi0 = 4;
24      private double _dz0 = 100.;
25  
26      public SectorManager() {
27  
28          //  Set the default sector parameters
29          setSectorParams(_nphi0, _dz0);
30  
31          //  Create the list of sectors with hits
32          _sectorlist = new ArrayList<Sector>();
33  
34          //  Create a map to locate a sector using it's ID
35          _sectormap = new HashMap<String, Sector>();
36  
37          //  Create a map to locate the list of sectors for a given layer
38          _slistmap = new HashMap<String, List<Sector>>();
39      }
40  
41      public void AddHit(HelicalTrackHit hit) {
42  
43          //  Get the sector identifier for this hit
44          String identifier = FindSectorIdentifier(hit);
45          
46          //  Retrieve the sector - create a new sector if one doesn't already exist
47          Sector sector;
48          if (!_sectormap.containsKey(identifier)) {
49              sector = CreateSector(hit);
50              _sectorlist.add(sector);
51              _sectormap.put(identifier, sector);
52  
53              //  See if we need to create a new list of Sensors for this detector layer
54              String lyrid = sector.LayerID();
55              if (!_slistmap.containsKey(lyrid)) {
56                  List<Sector> slist = new ArrayList<Sector>();
57                  _slistmap.put(lyrid, slist);
58              }
59  
60              //  Update the list of sensors for this layer
61              _slistmap.get(lyrid).add(sector);
62  
63          } else {
64              sector = _sectormap.get(identifier);
65          }
66  
67          //  Add the hit to the sector
68          sector.addHit(hit);
69      }
70  
71      public List<Sector> getAllSectors() {
72          return _sectorlist;
73      }
74  
75      public List<Sector> getSectors(SeedLayer layer) {
76          String layerID = layer.LayerID();
77          List<Sector> sectors;
78          if (_slistmap.containsKey(layerID)) {
79              sectors = _slistmap.get(layerID);
80          } else {
81              sectors = new ArrayList<Sector>();
82          }
83          return sectors;
84      }
85  
86      public void Initialize() {
87          _sectorlist.clear();
88          _sectormap.clear();
89          _slistmap.clear();
90      }
91  
92      public void setSectorParams(int nphi, double dz) {
93          _nphi = nphi;
94          _dphi = 2. * Math.PI / _nphi;
95          _dz = dz;
96      }
97  
98      public void setSectorParams(List<SeedStrategy> slist, double bfield, double rtrk) {
99  
100         //  Default to the default sectoring
101         int nphi = _nphi0;
102         double dz = _dz0;
103 
104         //  See if we have defined strategies
105         if (slist != null) {
106             int nstrat = slist.size();
107             if (nstrat > 0) {
108 
109                 //  Find the average pTMin and MaxZ0
110                 double dzsum = 0.;
111                 double ptsum = 0.;
112                 for (SeedStrategy strategy : slist) {
113                     ptsum += strategy.getMinPT();
114                     dzsum += strategy.getMaxZ0();
115                 }
116                 double ptave = ptsum / nstrat;
117                 double dzave = dzsum / nstrat;
118 
119                 //  If there is a bfield defined, set the size of a phi
120                 //  segmentation slice to half the change in angle for a
121                 //  the average minimum momentum particle
122                 if (bfield > 0.) {
123                     double RMin = ptave / (Constants.fieldConversion * bfield);
124                     double dphi = Math.atan(rtrk / (2. * RMin));
125                     nphi = (int) Math.floor(2. * Math.PI / dphi);
126                 }
127 
128                 //  Set the z sectoring to match the average MaxZ0
129                 dz = dzave;
130             }
131         }
132 
133         //  Save the sector parameters
134         setSectorParams(nphi, dz);
135 
136         return;
137     }
138 
139     private Sector CreateSector(HelicalTrackHit hit) {
140         String identifier = FindSectorIdentifier(hit);
141         String lyrid = hit.getLayerIdentifier();
142         int phibin = PhiBin(hit);
143         int zbin = ZBin(hit);
144         double phimin = PhiMin(phibin);
145         double phimax = PhiMax(phibin);
146         double zmin = ZMin(zbin);
147         double zmax = ZMax(zbin);
148         return new Sector(identifier, lyrid, phibin, zbin, phimin, phimax, zmin, zmax);
149     }
150 
151     private String FindSectorIdentifier(HelicalTrackHit hit) {
152         String layerID = hit.getLayerIdentifier();
153         int phibin = PhiBin(hit);
154         int zbin = ZBin(hit);
155         return SectorID(layerID, phibin, zbin);
156     }
157 
158     private String SectorID(String layerID, int phibin, int zbin) {
159         return layerID + "phi" + phibin + "z" + zbin;
160     }
161 
162     private int PhiBin(HelicalTrackHit hit) {
163         return (int) Math.floor(hit.phi() / _dphi);
164     }
165 
166     protected int ZBin(HelicalTrackHit hit) {
167         return (int) Math.floor(z(hit) / _dz);
168     }
169 
170     private double PhiMin(int phibin) {
171         return phibin * _dphi;
172     }
173 
174     private double PhiMax(int phibin) {
175         return (phibin + 1) * _dphi;
176     }
177 
178     private double ZMin(int zbin) {
179         return zbin * _dz;
180     }
181 
182     private double ZMax(int zbin) {
183         return (zbin + 1) * _dz;
184     }
185 
186     public static double z(HelicalTrackHit hit) {
187         double z;
188         if (hit.BarrelEndcapFlag() == BarrelEndcapFlag.BARREL) {
189             z = hit.z();
190         } else {
191             //  If this is an endcap disk, use the r coordinate rather than z
192             z = hit.r();
193         }
194         return z;
195     }
196 }