Skip to content

Commit

Permalink
feat: introduce digitization (#663)
Browse files Browse the repository at this point in the history
  • Loading branch information
asalzburger committed Feb 2, 2021
1 parent f61a219 commit bb07ac1
Show file tree
Hide file tree
Showing 26 changed files with 1,040 additions and 60 deletions.
4 changes: 0 additions & 4 deletions Core/include/Acts/Utilities/BinningType.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -6,10 +6,6 @@
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.

///////////////////////////////////////////////////////////////////
// BinningType.h, Acts project
///////////////////////////////////////////////////////////////////

#pragma once
#include <string>
#include <vector>
Expand Down
1 change: 1 addition & 0 deletions Examples/Algorithms/Digitization/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
add_library(
ActsExamplesDigitization SHARED
src/DigitizationAlgorithm.cpp
src/PlanarSteppingAlgorithm.cpp
src/HitSmearing.cpp
src/SmearingAlgorithm.cpp
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,184 @@
// This file is part of the Acts project.
//
// Copyright (C) 2021 CERN for the benefit of the Acts project
//
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.

#pragma once

#include "Acts/Definitions/Algebra.hpp"
#include "Acts/Definitions/TrackParametrization.hpp"
#include "Acts/Geometry/GeometryHierarchyMap.hpp"
#include "ActsExamples/Digitization/DigitizationConfig.hpp"
#include "ActsExamples/EventData/Measurement.hpp"
#include "ActsExamples/EventData/SimHit.hpp"
#include "ActsExamples/Framework/BareAlgorithm.hpp"
#include "ActsExamples/Framework/RandomNumbers.hpp"
#include "ActsFatras/Digitization/Channelizer.hpp"
#include "ActsFatras/Digitization/PlanarSurfaceDrift.hpp"
#include "ActsFatras/Digitization/PlanarSurfaceMask.hpp"

#include <memory>
#include <string>
#include <tuple>
#include <utility>
#include <variant>
#include <vector>

namespace Acts {
class Surface;
class TrackingGeometry;
} // namespace Acts

namespace ActsExamples {

/// Algorithm that turns simulated hits into measurements by truth smearing.
class DigitizationAlgorithm final : public BareAlgorithm {
public:
struct Config {
/// Input collection of simulated hits.
std::string inputSimHits;
/// Output source links collection.
std::string outputSourceLinks;
/// Output measurements collection.
std::string outputMeasurements;
/// Output collection to map measured hits to contributing particles.
std::string outputMeasurementParticlesMap;
/// Output collection to map measured hits to simulated hits.
std::string outputMeasurementSimHitsMap;
/// Tracking geometry required to access global-to-local transforms.
std::shared_ptr<const Acts::TrackingGeometry> trackingGeometry = nullptr;
/// Random numbers tool.
std::shared_ptr<const RandomNumbers> randomNumbers = nullptr;
/// The digitizers per GeometryIdentifier
Acts::GeometryHierarchyMap<DigitizationConfig> digitizationConfigs;
};

/// Construct the smearing algorithm.
///
/// @param cfg is the algorithm configuration
/// @param lvl is the logging level
DigitizationAlgorithm(Config cfg, Acts::Logging::Level lvl);

/// Build measurement from simulation hits at input.
///
/// @param ctx is the algorithm context with event information
/// @return a process code indication success or failure
ProcessCode execute(const AlgorithmContext& ctx) const final override;

private:
/// Nested struct for digitized parameters
struct DigitizedParameters {
std::vector<Acts::BoundIndices> indices = {};
std::vector<Acts::ActsScalar> values = {};
std::vector<Acts::ActsScalar> variances = {};
std::vector<Acts::ActsScalar> trueValues = {};
};

/// Helper method for the geometric channelizing part
///
/// @param geoCfg is the geometric digitization configuration
/// @param hit the Simultated hit
/// @param surface the Surface on which this is supposed to happen
/// @param gctx the Geometry context
/// @param rng the Random number engine for the drift smearing
///
/// @return the list of channels
std::vector<ActsFatras::Channelizer::ChannelSegment> channelizing(
const GeometricDigitizationConfig& geoCfg, const SimHit& hit,
const Acts::Surface& surface, const Acts::GeometryContext& gctx,
RandomEngine& rng) const;

/// Helper method for creating digitized parameters from clusters
///
/// @todo ADD random smearing
/// @param geoCfg is the geometric digitization configuration
/// @param channels are the input channels
/// @param rng the Random number engine for the charge generation smearing
///
/// @return the list of digitized parameters
DigitizedParameters localParameters(
const GeometricDigitizationConfig& geoCfg,
const std::vector<ActsFatras::Channelizer::ChannelSegment>& channels,
RandomEngine& rng) const;

/// Helper method for created a measurement from digitized parameters
///
/// @param dParams The digitized parameters of variable size
/// @param isl The indexed source link for the measurement
///
/// @return a variant measurement
Measurement createMeasurement(const DigitizedParameters& dParams,
const IndexSourceLink& isl) const
noexcept(false);

/// Nested smearer struct that holds geometric digitizer and smearing
/// Support up to 4 dimensions.
template <size_t kSmearDIM>
struct CombinedDigitizer {
GeometricDigitizationConfig geometric;
ActsFatras::BoundParametersSmearer<RandomEngine, kSmearDIM> smearing;
};

// Support max 4 digitization dimensions - either digital or smeared
using Digitizer = std::variant<CombinedDigitizer<0>, CombinedDigitizer<1>,
CombinedDigitizer<2>, CombinedDigitizer<3>,
CombinedDigitizer<4>>;

/// Configuration of the Algorithm
Config m_cfg;
/// Digitizers within geometry hierarchy
Acts::GeometryHierarchyMap<Digitizer> m_digitizers;
/// Geometric digtizers
ActsFatras::PlanarSurfaceDrift m_surfaceDrift;
ActsFatras::PlanarSurfaceMask m_surfaceMask;
ActsFatras::Channelizer m_channelizer;

/// Contruct the constituents of a measurement.
///
/// @tparam kMeasDIM the full dimension of the measurement
///
/// @param dParams the struct of arrays of parameters to be created
///
/// @return a tuple of constituents for a measurement
template <size_t kMeasDIM>
std::tuple<std::array<Acts::BoundIndices, kMeasDIM>,
Acts::ActsVector<kMeasDIM>, Acts::ActsSymMatrix<kMeasDIM>>
measurementConstituents(const DigitizedParameters& dParams) const {
std::array<Acts::BoundIndices, kMeasDIM> indices;
Acts::ActsVector<kMeasDIM> par;
Acts::ActsSymMatrix<kMeasDIM> cov =
Acts::ActsSymMatrix<kMeasDIM>::Identity();
for (Eigen::Index ei = 0; ei < static_cast<Eigen::Index>(kMeasDIM); ++ei) {
indices[ei] = dParams.indices[ei];
par[ei] = dParams.values[ei];
cov(ei, ei) = dParams.variances[ei];
}
return {indices, par, cov};
}

/// Construct a fixed-size smearer from a configuration.
///
/// It's templated on the smearing dimention given by @tparam kSmearDIM
///
/// @param cfg Is the digitization configuration input
///
/// @return a variant of a Digitizer
template <size_t kSmearDIM>
static Digitizer makeDigitizer(const DigitizationConfig& cfg) {
CombinedDigitizer<kSmearDIM> impl;
// Copy the geometric configuration
impl.geometric = cfg.geometricDigiConfig;
// Prepare the smearing configuration
for (size_t i = 0; i < kSmearDIM; ++i) {
impl.smearing.indices[i] = cfg.smearingDigiConfig.at(i).index;
impl.smearing.smearFunctions[i] =
cfg.smearingDigiConfig.at(i).smearFunction;
}
return impl;
}
};

} // namespace ActsExamples
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
// This file is part of the Acts project.
//
// Copyright (C) 2021 CERN for the benefit of the Acts project
//
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.

#pragma once

#include "Acts/Definitions/Algebra.hpp"
#include "Acts/Utilities/BinUtility.hpp"
#include "Acts/Utilities/BinningType.hpp"
#include "ActsExamples/Digitization/SmearingConfig.hpp"
#include "ActsExamples/Framework/RandomNumbers.hpp"
#include "ActsFatras/Digitization/UncorrelatedHitSmearer.hpp"

#include <functional>

namespace ActsExamples {

/// Takes as an argument the position, and a random engine
/// @return drift direction in local 3D coordinates
using DriftGenerator =
std::function<Acts::Vector3(const Acts::Vector3&, RandomEngine&)>;
/// Takes as an argument the path length, the drift length, and a random engine
/// @return a charge to which the threshold can be applied
using ChargeGenerator = std::function<Acts::ActsScalar(
Acts::ActsScalar, Acts::ActsScalar, RandomEngine&)>;
/// Takes as an argument the clsuter size and an random engine
/// @return a vector of uncorrelated covariance values
using VarianceGenerator =
std::function<std::vector<Acts::ActsScalar>(size_t, size_t, RandomEngine&)>;

/// Configuration struct for geometric digitization
///
/// If this is defined, then the geometric digitization
/// will create clusters with cells.
/// The BinUtility defines the segmentation and which parameters
/// are defined by this.
///
struct GeometricDigitizationConfig {
std::vector<Acts::BoundIndices> indices = {};
Acts::BinUtility segmentation;
/// Drift generation
DriftGenerator drift = [](const Acts::Vector3&,
RandomEngine&) -> Acts::Vector3 {
return Acts::Vector3(0., 0., 0.);
};
double thickness = 0.;
/// Charge generation
ChargeGenerator charge = [](Acts::ActsScalar path, Acts::ActsScalar,
RandomEngine&) -> Acts::ActsScalar {
return path;
};
double threshold = 0.;
/// Position and Covariance generation
bool digital = false;
VarianceGenerator variances =
[](size_t, size_t, RandomEngine&) -> std::vector<Acts::ActsScalar> {
return {};
};
};

/// Configuration struct for the Digitization algorithm
///
/// It contains:
/// - optional GeometricConfig
/// - optional SmearingConfig
struct DigitizationConfig {
GeometricDigitizationConfig geometricDigiConfig;
SmearingConfig smearingDigiConfig = {};
};

} // namespace ActsExamples
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@

#pragma once

#include "ActsExamples/Digitization/DigitizationAlgorithm.hpp"
#include "ActsExamples/Digitization/SmearingAlgorithm.hpp"
#include "ActsExamples/Utilities/OptionsFwd.hpp"

Expand All @@ -24,5 +25,11 @@ void addDigitizationOptions(Description& desc);
/// @param variables The variables to read from
SmearingAlgorithm::Config readSmearingConfig(const Variables& variables);

/// Read Digitization Config from the options.
///
/// @param variables The variables to read from
DigitizationAlgorithm::Config readDigitizationConfig(
const Variables& variables);

} // namespace Options
} // namespace ActsExamples
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,8 @@
#include <cmath>
#include <limits>
#include <random>
#include <string>
#include <tuple>
#include <utility>

namespace ActsExamples {
Expand Down Expand Up @@ -50,6 +52,7 @@ struct Gauss {
/// indicating the truncation
struct GaussTrunc {
std::normal_distribution<> dist{0., 1.};

std::pair<double, double> range = {std::numeric_limits<double>::lowest(),
std::numeric_limits<double>::max()};

Expand Down Expand Up @@ -125,9 +128,9 @@ struct Uniform {
(range_.second - range_.first) / pitch, range_.first,
range_.second) {}

/// Constructor with a bin utility in order to get the bin borders.
/// Constructor with a binning data in order to get the bin borders.
///
/// @param bu the bin utility which d
/// @param bu the binning data
Uniform(Acts::BinningData&& bd) : binningData(std::move(bd)) {}

/// Call operator for the SmearFunction caller interface.
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
// This file is part of the Acts project.
//
// Copyright (C) 2020 CERN for the benefit of the Acts project
// Copyright (C) 2020-2021 CERN for the benefit of the Acts project
//
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
Expand All @@ -10,9 +10,9 @@

#include "Acts/Definitions/TrackParametrization.hpp"
#include "Acts/Geometry/GeometryHierarchyMap.hpp"
#include "ActsExamples/Digitization/SmearingConfig.hpp"
#include "ActsExamples/Framework/BareAlgorithm.hpp"
#include "ActsExamples/Framework/RandomNumbers.hpp"
#include "ActsFatras/Digitization/UncorrelatedHitSmearer.hpp"

#include <memory>
#include <string>
Expand All @@ -29,16 +29,6 @@ namespace ActsExamples {
/// Algorithm that turns simulated hits into measurements by truth smearing.
class SmearingAlgorithm final : public BareAlgorithm {
public:
struct ParameterSmearerConfig {
// Which parameter does this apply to.
Acts::BoundIndices index = Acts::eBoundSize;
// The smearing function for this parameter.
ActsFatras::SingleParameterSmearFunction<RandomEngine> smearFunction;
};
// The configured indices must be unique, i.e. each one can only appear once
// in a smearer configuration.
using SmearerConfig = std::vector<ParameterSmearerConfig>;

struct Config {
/// Input collection of simulated hits.
std::string inputSimHits;
Expand All @@ -55,7 +45,7 @@ class SmearingAlgorithm final : public BareAlgorithm {
/// Random numbers tool.
std::shared_ptr<const RandomNumbers> randomNumbers = nullptr;
/// The smearers per GeometryIdentifier
Acts::GeometryHierarchyMap<SmearerConfig> smearers;
Acts::GeometryHierarchyMap<SmearingConfig> smearers;
};

/// Construct the smearing algorithm.
Expand Down Expand Up @@ -83,7 +73,7 @@ class SmearingAlgorithm final : public BareAlgorithm {

/// Construct a fixed-size smearer from a configuration.
template <size_t kSize>
static Smearer makeSmearer(const SmearerConfig& cfg) {
static Smearer makeSmearer(const SmearingConfig& cfg) {
ActsFatras::BoundParametersSmearer<RandomEngine, kSize> impl;
for (size_t i = 0; i < kSize; ++i) {
impl.indices[i] = cfg.at(i).index;
Expand Down

0 comments on commit bb07ac1

Please sign in to comment.