mergeron 2024.739091.2__tar.gz → 2024.739097.2__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (39) hide show
  1. mergeron-2024.739097.2/PKG-INFO +130 -0
  2. mergeron-2024.739097.2/README.rst +83 -0
  3. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/pyproject.toml +4 -4
  4. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/__init__.py +1 -18
  5. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/core/damodaran_margin_data.py +1 -1
  6. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/core/ftc_merger_investigations_data.py +4 -5
  7. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/ext/xlsxw_helper.py +8 -0
  8. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/gen/__init__.py +24 -8
  9. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/gen/_data_generation_functions.py +210 -49
  10. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/gen/data_generation.py +51 -43
  11. mergeron-2024.739097.2/src/mergeron/gen/market_sample.py +143 -0
  12. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/gen/upp_tests.py +3 -8
  13. mergeron-2024.739091.2/PKG-INFO +0 -110
  14. mergeron-2024.739091.2/README.rst +0 -61
  15. mergeron-2024.739091.2/src/mergeron/gen/market_sample.py +0 -75
  16. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/License.txt +0 -0
  17. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/core/__init__.py +0 -0
  18. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/core/guidelines_boundaries.py +0 -0
  19. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/core/guidelines_boundary_functions.py +0 -0
  20. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/core/guidelines_boundary_functions_extra.py +0 -0
  21. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/core/pseudorandom_numbers.py +0 -0
  22. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/data/__init__.py +0 -0
  23. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/data/damodaran_margin_data.xls +0 -0
  24. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/data/damodaran_margin_data_dict.msgpack +0 -0
  25. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/data/ftc_invdata.msgpack +0 -0
  26. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/data/jinja2_LaTeX_templates/clrrate_cis_summary_table_template.tex.jinja2 +0 -0
  27. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/data/jinja2_LaTeX_templates/ftcinvdata_byhhianddelta_table_template.tex.jinja2 +0 -0
  28. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/data/jinja2_LaTeX_templates/ftcinvdata_summary_table_template.tex.jinja2 +0 -0
  29. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/data/jinja2_LaTeX_templates/ftcinvdata_summarypaired_table_template.tex.jinja2 +0 -0
  30. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/data/jinja2_LaTeX_templates/mergeron.cls +0 -0
  31. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/data/jinja2_LaTeX_templates/mergeron_table_collection_template.tex.jinja2 +0 -0
  32. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/data/jinja2_LaTeX_templates/setup_tikz_tables.tex +0 -0
  33. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/demo/__init__.py +0 -0
  34. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/demo/visualize_empirical_margin_distribution.py +0 -0
  35. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/ext/__init__.py +0 -0
  36. {mergeron-2024.739091.2/src/mergeron/core → mergeron-2024.739097.2/src/mergeron/ext}/proportions_tests.py +0 -0
  37. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/ext/tol_colors.py +0 -0
  38. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/gen/enforcement_stats.py +0 -0
  39. {mergeron-2024.739091.2 → mergeron-2024.739097.2}/src/mergeron/py.typed +0 -0
@@ -0,0 +1,130 @@
1
+ Metadata-Version: 2.1
2
+ Name: mergeron
3
+ Version: 2024.739097.2
4
+ Summary: Merger Policy Analysis using Python
5
+ License: MIT
6
+ Keywords: merger policy analysis,merger guidelines,merger screening,policy presumptions,concentration standards,upward pricing pressure,GUPPI
7
+ Author: Murthy Kambhampaty
8
+ Author-email: smk@capeconomics.com
9
+ Requires-Python: >=3.12,<4.0
10
+ Classifier: Development Status :: 4 - Beta
11
+ Classifier: Environment :: Console
12
+ Classifier: Intended Audience :: End Users/Desktop
13
+ Classifier: Intended Audience :: Science/Research
14
+ Classifier: License :: OSI Approved :: MIT License
15
+ Classifier: Operating System :: OS Independent
16
+ Classifier: Programming Language :: Python
17
+ Classifier: Programming Language :: Python :: 3
18
+ Classifier: Programming Language :: Python :: 3.12
19
+ Classifier: Programming Language :: Python :: 3 :: Only
20
+ Classifier: Programming Language :: Python :: Implementation :: CPython
21
+ Requires-Dist: aenum (>=3.1.15,<4.0.0)
22
+ Requires-Dist: attrs (>=23.2)
23
+ Requires-Dist: bs4 (>=0.0.1)
24
+ Requires-Dist: certifi (>=2023.11.17)
25
+ Requires-Dist: google-re2 (>=1.1)
26
+ Requires-Dist: jinja2 (>=3.1)
27
+ Requires-Dist: joblib (>=1.3)
28
+ Requires-Dist: lxml (>=5.0)
29
+ Requires-Dist: matplotlib (>=3.8)
30
+ Requires-Dist: mpmath (>=1.3)
31
+ Requires-Dist: msgpack (>=1.0)
32
+ Requires-Dist: msgpack-numpy (>=0.4)
33
+ Requires-Dist: numpy (>=1.26,<2.0)
34
+ Requires-Dist: openpyxl (>=3.1.2)
35
+ Requires-Dist: poetry-plugin-export (>=1.8.0,<2.0.0)
36
+ Requires-Dist: requests (>=2.31)
37
+ Requires-Dist: requests-toolbelt (>=1.0.0)
38
+ Requires-Dist: scipy (>=1.12)
39
+ Requires-Dist: sympy (>=1.12)
40
+ Requires-Dist: tables (>=3.8)
41
+ Requires-Dist: types-beautifulsoup4 (>=4.11.2)
42
+ Requires-Dist: types-requests (>=2.31.0)
43
+ Requires-Dist: xlrd (>=2.0.1,<3.0.0)
44
+ Requires-Dist: xlsxwriter (>=3.1)
45
+ Description-Content-Type: text/x-rst
46
+
47
+ mergeron: Merger Policy Analysis using Python
48
+ =============================================
49
+
50
+ Analyze the sets of mergers conforming to concentration and diversion ratio bounds. Analyze intrinsic enforcement rates, and intrinsic clearance rates, under concentration, diversion ratio, GUPPI, CMCR, and IPR bounds using generated data with specified distributions of market shares, price-cost margins, firm counts, and prices, optionally imposing restrictions impled by statutory filing thresholds and/or Bertrand-Nash oligopoly with MNL demand. Download and analyze merger investigations data published by the U.S. Federal Trade Commission in various reports on extended merger investigations (Second Requests) during 1996 to 2011.
51
+
52
+ Intrinsic enforcement rates and intrinsice clearance rates are distinguished from *observed* clearance and enforcement rates in that the former are derived from analyzing theorectical predictions regarding firm conduct against enforcement thresholds, treating enforcement policy as exogenous to firm conduct. Depending on the merger enforcement regime, or merger control regime, intrinsic enforcement rates may also not be the complement of intrinsic clearance rates, i.e, it is not necessarily true that the intrinsic clearance rate estimate for a given enforcement regime is 1 minus the intrinsic enforcement rate. In contrast, observed enforcement rates reflect the deterrent effects of merger enforcement on firm conduct as well as the effects of merger screening on the level of enforcement, and, ny definition, the observed clearance rate is 1 minus the observed enforement rate.
53
+
54
+ Introduction
55
+ ------------
56
+
57
+ Module :code:`mergeron.core.guidelines_boundaries` includes classes for specifying concentration bounds (:code:`mergeron.core.guidelines_boundaries.ConcentrationBoundary`) and diversion-ratio bounds (:code:`mergeron.core.guidelines_boundaries.DiversionRatioBoundary`), with automatic generation of boundary (as an array of share-pairs) and area. This module also includes a function for generating plots of concentation and diversion-ratio boundaries, and functions for mapping GUPPI standards to concentration (ΔHHI) standards, and vice-versa.
58
+
59
+ Module :code:`mergeron.gen.market_sample` includes the :code:`mergeron.gen.market_sample.MarketSample` with methods for, (i) generating sample data under a rich specification of shares, diversion ratios, margins, prices, and HSR filing requirements, and (ii) for estimating enforcement or clearance rates under specified enforcement regimes given a method of aggregating diversion ratio or GUPPI estimates for the firms in a merger. Notably. share are genarated not just for markets with a fixed number of firms, but for markets with multiple firm-count weights, which may be left unspecified or explicitly specified.
60
+
61
+ Unless otherwise specified, merging-firm shares are drawn with uniform distribution over the space :math:`s_1 + s_2 \leqslant 1` for an unspecified number of firms. Alternatively, shares may be drawn from the Dirichlet distribution, with specified shape parameters (see :code:`mergeron.gen.ShareContants`. When drawing shares from the Dirichlet distribution, the user passes, using :code:`mergeron.gen.MarketSpec.ShareSpec.firm_count_weights`, a vector of weights specifying the frequency distribution over sequential firm counts, e.g., :code:`[133, 184, 134, 52, 32, 10, 12, 4, 3]` to specify shares drawn from Dirichlet distributions with 2 to 10 pre-merger firms distributed as in data for FTC merger investigations during 1996--2003 (See, for example, Table 4.1 of `FTC, Horizontal Merger Investigations Data, Fiscal Years 1996--2003 (Revised: August 31, 2004) <https://www.ftc.gov/sites/default/files/documents/reports/horizontal-merger-investigation-data-fiscal-years-1996-2003/040831horizmergersdata96-03.pdf>`_). If :code:`mergeron.gen.MarketSpec.ShareSpec.firm_count_weights` is not assigned a value when defining :code:`mergeron.gen.MarketSpec.ShareSpec` (which has type, :code:`mergeron.gen.ShareSpec`), the default values is used, with results in a sample of markets with 2 to 6 firms with equal relative frequency.
62
+
63
+ Recapture rates can be specifed as, "proportional", "inside-out", "outside-in" (see :code:`mergeron.RECConstants`. The "inside-out" specification results in recapture ratios consistent with merging-firms' in-market shares and a default recapture rate. The "outside-in" specification yields diversion ratios from purchase probabilities drawn at random for :math:`N+1` goods, from which are derived market shares and recapture rates for the :math:`N` goods in the putative market (see, :code:`mergeron.gen.DiversionRatioSpec`). The "outside-in" specification is invalid when the distribution of markets over firm-count is unspecified, i.e., when :code:`mergeron.gen.MarketSpec.ShareSpec.dist_type ==`:code:`mergeron.gen.ShareContants.UNI`.
64
+
65
+ Price-cost-margins may be specified as having uniform distribution, Beta distribution (including a bounded Beta distribution with specified mean and variance), or an empirical distribution. The empirical margin distribution is based on resampling margin data published by Prof. Damodaran of NYU Stern School of Business (see Notes), using an estimated Gaussian KDE. The second merging firm's margin may be specified as symmetric, i.i.d., or subject to equilibrium conditions for (profit-mazimization in) Bertrand-Nash oligopoly with MNL demand (see, :code:`mergeron.gen.PCMSpec`).
66
+
67
+ Prices may be specified as symmetric or asymmetric, and in the latter case, the direction of correlation between merging firm prices, if any, can also be specified (see, :code:`mergeron.gen.PriceSpec`).
68
+
69
+ The market sample may be restricted to mergers meeting the HSR filing requirement under two alternative approaches: in the one, the smaller of the two merging firms meets the HSR filing threshold for the smaller (acquired) firm. In the other, the :math:`n`-th firm's size matches the size requirement for the smaller merging firm (see, :code:`mergeron.gen.SSZConstants`). The second assumption avoids the unfortunate assumption in the first that, within the resulting sample, the larger merging firm be at least 10 times as large as the smaller merging firm, as a consequence of the full definition of the HSR filing requirement.
70
+
71
+ The full specification of a market sample is given in a :code:`mergeron.gen.market_sample.MarketSample` object, including the above parameters. Data are drawn by invoking :code:`mergeron.gen.market_sample.MarketSample.generate_sample` which adds a :code:`data` property of class, :code:`mergeron.gen.MarketDataSample`. Enforcement or clearance counts are computed by invoking :code:`mergeron.gen.market_sample.MarketSample.estimate_enf_counts`, which adds an :code:`enf_counts` property of class :code:`mergeron.gen.UPPTestsCounts`. For fast, parallel generation of enforcement or clearance counts over large market data samples that ordinarily would exceed available limits on machine memory, the user can invoke the method :code:`estimate_enf_counts` on a :code:`mergeron.gen.market_sample.MarketSample` object without first invoking :code:`generate_sample`. Note, however, that this strategy does not retain the market sample in memory in the interests of conserving memory and maintaining high performance (the user can specify that the market sample and enforcement statistics be stored to permanent storage; when saving to current PCIe NVMe storage, the perfomance penalty is slight, but can be considerable if saving to SATA storage).
72
+
73
+ Enforcement statistics based on FTC investigations data and test data are printed to screen or rendered to LaTex files (for processing into publication-quality tables) using methods provided in :code:`mergeron.gen.enforcement_stats`.
74
+
75
+ Programs demonstrating the use of this package are included in the sub-package, :code:`mergeron.demo`.
76
+
77
+ This package includes a class, :code:`mergeron.core.pseudorandom_numbers.MulithreadedRNG` for generating random numbers with selected continuous distribution over specified parameters, and with CPU multithreading on machines with multiple virtual, logical, or physical CPU cores. This class is an adaptation from the documentation of the :code:`numpy` package, from the discussion on `multithreaded random-number generation <https://numpy.org/doc/stable/reference/random/multithreading.html>_`; the version included here permits selection of the distribution with pre-tests to catch and inform on common errors. To access these directly:
78
+
79
+ .. code-block:: python
80
+
81
+ import mergeron.core.pseudorandom_numbers as prng
82
+
83
+ Documentation for this package is in the form of the API Reference. Documentation for individual functions and classes is accessible within a python shell. For example:
84
+
85
+ .. code-block:: python
86
+
87
+ import mergeron.core.market_sample as market_sample
88
+
89
+ help(market_sample.MarketSample)
90
+
91
+ "Extras" Subpackage
92
+ ---------------------
93
+
94
+ The "Extras" sub-package includes a small number of modules potentially useful to users, but which do not implement the principal functions of the package, and are hence considered "extras" or "external" modules. One of these modules is, in fact, repackaged here although published independently.
95
+
96
+ On of the external modules provides methods for estimating confidence intervals for proportions and for contrasts (differences) in proportions. This module improve is coded for conformance to the literature and to results from the corresponding modules in :code:`R`. Although written from scratch, the APIs implemented in the module included here are designed for consistency with the APIs in, :code:`statsmodels.stats.proportion` from the package, :code:`statsmodels` (https://pypi.org/project/statsmodels/). To access these directly:
97
+
98
+ .. code-block:: python
99
+
100
+ import mergeron.ext.proportions_tests as prci
101
+
102
+ Module :code:`mergeron.ext.xlsxw_helper` is useful for writing highly formatted output to spreadsheets with xlsx format. The class, :code:`mergeron.ext.xlsxw_helper.CFmt` and function, :code:`mergeron.ext.xlsxw_helper.array_to_sheet` are of particular interest, and can be accessed as :code:`xlh.CFmt` and :code:`xlh.array_to_sheet` with the following import:
103
+
104
+ .. code-block:: python
105
+
106
+ import mergeron.ext.xlsxw_helper as xlsxw_helper
107
+
108
+ A recent version of Paul Tol's python module, :code:`tol_colors.py`, which provides high-contrast color schemes for making displays with improved visibility for individuals with color-blindness, is redistributed within this package. Other than re-formatting and type annotation, the :code:`mergeron.ext.tol_colors` module is re-distributed as downloaded from, https://personal.sron.nl/~pault/data/tol_colors.py. The :code:`tol_colors.py` module is distributed under the Standard 3-clause BSD license. To access the :code:`mergeron.ext.tol_colors` module directly:
109
+
110
+ .. code-block:: python
111
+
112
+ import mergeron.ext.tol_colors as ptc
113
+
114
+ .. image:: https://img.shields.io/endpoint?url=https://python-poetry.org/badge/v0.json
115
+ :alt: Poetry
116
+ :target: https://python-poetry.org/
117
+
118
+ .. image:: https://img.shields.io/endpoint?url=https://raw.githubusercontent.com/astral-sh/ruff/main/assets/badge/v2.json
119
+ :alt: Ruff
120
+ :target: https://github.com/astral-sh/ruff
121
+
122
+ .. image:: https://www.mypy-lang.org/static/mypy_badge.svg
123
+ :alt: Checked with mypy
124
+ :target: https://mypy-lang.org/
125
+
126
+ .. image:: https://img.shields.io/badge/License-MIT-yellow.svg
127
+ :alt: License: MIT
128
+ :target: https://opensource.org/licenses/MIT
129
+
130
+
@@ -0,0 +1,83 @@
1
+ mergeron: Merger Policy Analysis using Python
2
+ =============================================
3
+
4
+ Analyze the sets of mergers conforming to concentration and diversion ratio bounds. Analyze intrinsic enforcement rates, and intrinsic clearance rates, under concentration, diversion ratio, GUPPI, CMCR, and IPR bounds using generated data with specified distributions of market shares, price-cost margins, firm counts, and prices, optionally imposing restrictions impled by statutory filing thresholds and/or Bertrand-Nash oligopoly with MNL demand. Download and analyze merger investigations data published by the U.S. Federal Trade Commission in various reports on extended merger investigations (Second Requests) during 1996 to 2011.
5
+
6
+ Intrinsic enforcement rates and intrinsice clearance rates are distinguished from *observed* clearance and enforcement rates in that the former are derived from analyzing theorectical predictions regarding firm conduct against enforcement thresholds, treating enforcement policy as exogenous to firm conduct. Depending on the merger enforcement regime, or merger control regime, intrinsic enforcement rates may also not be the complement of intrinsic clearance rates, i.e, it is not necessarily true that the intrinsic clearance rate estimate for a given enforcement regime is 1 minus the intrinsic enforcement rate. In contrast, observed enforcement rates reflect the deterrent effects of merger enforcement on firm conduct as well as the effects of merger screening on the level of enforcement, and, ny definition, the observed clearance rate is 1 minus the observed enforement rate.
7
+
8
+ Introduction
9
+ ------------
10
+
11
+ Module :code:`mergeron.core.guidelines_boundaries` includes classes for specifying concentration bounds (:code:`mergeron.core.guidelines_boundaries.ConcentrationBoundary`) and diversion-ratio bounds (:code:`mergeron.core.guidelines_boundaries.DiversionRatioBoundary`), with automatic generation of boundary (as an array of share-pairs) and area. This module also includes a function for generating plots of concentation and diversion-ratio boundaries, and functions for mapping GUPPI standards to concentration (ΔHHI) standards, and vice-versa.
12
+
13
+ Module :code:`mergeron.gen.market_sample` includes the :code:`mergeron.gen.market_sample.MarketSample` with methods for, (i) generating sample data under a rich specification of shares, diversion ratios, margins, prices, and HSR filing requirements, and (ii) for estimating enforcement or clearance rates under specified enforcement regimes given a method of aggregating diversion ratio or GUPPI estimates for the firms in a merger. Notably. share are genarated not just for markets with a fixed number of firms, but for markets with multiple firm-count weights, which may be left unspecified or explicitly specified.
14
+
15
+ Unless otherwise specified, merging-firm shares are drawn with uniform distribution over the space :math:`s_1 + s_2 \leqslant 1` for an unspecified number of firms. Alternatively, shares may be drawn from the Dirichlet distribution, with specified shape parameters (see :code:`mergeron.gen.ShareContants`. When drawing shares from the Dirichlet distribution, the user passes, using :code:`mergeron.gen.MarketSpec.ShareSpec.firm_count_weights`, a vector of weights specifying the frequency distribution over sequential firm counts, e.g., :code:`[133, 184, 134, 52, 32, 10, 12, 4, 3]` to specify shares drawn from Dirichlet distributions with 2 to 10 pre-merger firms distributed as in data for FTC merger investigations during 1996--2003 (See, for example, Table 4.1 of `FTC, Horizontal Merger Investigations Data, Fiscal Years 1996--2003 (Revised: August 31, 2004) <https://www.ftc.gov/sites/default/files/documents/reports/horizontal-merger-investigation-data-fiscal-years-1996-2003/040831horizmergersdata96-03.pdf>`_). If :code:`mergeron.gen.MarketSpec.ShareSpec.firm_count_weights` is not assigned a value when defining :code:`mergeron.gen.MarketSpec.ShareSpec` (which has type, :code:`mergeron.gen.ShareSpec`), the default values is used, with results in a sample of markets with 2 to 6 firms with equal relative frequency.
16
+
17
+ Recapture rates can be specifed as, "proportional", "inside-out", "outside-in" (see :code:`mergeron.RECConstants`. The "inside-out" specification results in recapture ratios consistent with merging-firms' in-market shares and a default recapture rate. The "outside-in" specification yields diversion ratios from purchase probabilities drawn at random for :math:`N+1` goods, from which are derived market shares and recapture rates for the :math:`N` goods in the putative market (see, :code:`mergeron.gen.DiversionRatioSpec`). The "outside-in" specification is invalid when the distribution of markets over firm-count is unspecified, i.e., when :code:`mergeron.gen.MarketSpec.ShareSpec.dist_type ==`:code:`mergeron.gen.ShareContants.UNI`.
18
+
19
+ Price-cost-margins may be specified as having uniform distribution, Beta distribution (including a bounded Beta distribution with specified mean and variance), or an empirical distribution. The empirical margin distribution is based on resampling margin data published by Prof. Damodaran of NYU Stern School of Business (see Notes), using an estimated Gaussian KDE. The second merging firm's margin may be specified as symmetric, i.i.d., or subject to equilibrium conditions for (profit-mazimization in) Bertrand-Nash oligopoly with MNL demand (see, :code:`mergeron.gen.PCMSpec`).
20
+
21
+ Prices may be specified as symmetric or asymmetric, and in the latter case, the direction of correlation between merging firm prices, if any, can also be specified (see, :code:`mergeron.gen.PriceSpec`).
22
+
23
+ The market sample may be restricted to mergers meeting the HSR filing requirement under two alternative approaches: in the one, the smaller of the two merging firms meets the HSR filing threshold for the smaller (acquired) firm. In the other, the :math:`n`-th firm's size matches the size requirement for the smaller merging firm (see, :code:`mergeron.gen.SSZConstants`). The second assumption avoids the unfortunate assumption in the first that, within the resulting sample, the larger merging firm be at least 10 times as large as the smaller merging firm, as a consequence of the full definition of the HSR filing requirement.
24
+
25
+ The full specification of a market sample is given in a :code:`mergeron.gen.market_sample.MarketSample` object, including the above parameters. Data are drawn by invoking :code:`mergeron.gen.market_sample.MarketSample.generate_sample` which adds a :code:`data` property of class, :code:`mergeron.gen.MarketDataSample`. Enforcement or clearance counts are computed by invoking :code:`mergeron.gen.market_sample.MarketSample.estimate_enf_counts`, which adds an :code:`enf_counts` property of class :code:`mergeron.gen.UPPTestsCounts`. For fast, parallel generation of enforcement or clearance counts over large market data samples that ordinarily would exceed available limits on machine memory, the user can invoke the method :code:`estimate_enf_counts` on a :code:`mergeron.gen.market_sample.MarketSample` object without first invoking :code:`generate_sample`. Note, however, that this strategy does not retain the market sample in memory in the interests of conserving memory and maintaining high performance (the user can specify that the market sample and enforcement statistics be stored to permanent storage; when saving to current PCIe NVMe storage, the perfomance penalty is slight, but can be considerable if saving to SATA storage).
26
+
27
+ Enforcement statistics based on FTC investigations data and test data are printed to screen or rendered to LaTex files (for processing into publication-quality tables) using methods provided in :code:`mergeron.gen.enforcement_stats`.
28
+
29
+ Programs demonstrating the use of this package are included in the sub-package, :code:`mergeron.demo`.
30
+
31
+ This package includes a class, :code:`mergeron.core.pseudorandom_numbers.MulithreadedRNG` for generating random numbers with selected continuous distribution over specified parameters, and with CPU multithreading on machines with multiple virtual, logical, or physical CPU cores. This class is an adaptation from the documentation of the :code:`numpy` package, from the discussion on `multithreaded random-number generation <https://numpy.org/doc/stable/reference/random/multithreading.html>_`; the version included here permits selection of the distribution with pre-tests to catch and inform on common errors. To access these directly:
32
+
33
+ .. code-block:: python
34
+
35
+ import mergeron.core.pseudorandom_numbers as prng
36
+
37
+ Documentation for this package is in the form of the API Reference. Documentation for individual functions and classes is accessible within a python shell. For example:
38
+
39
+ .. code-block:: python
40
+
41
+ import mergeron.core.market_sample as market_sample
42
+
43
+ help(market_sample.MarketSample)
44
+
45
+ "Extras" Subpackage
46
+ ---------------------
47
+
48
+ The "Extras" sub-package includes a small number of modules potentially useful to users, but which do not implement the principal functions of the package, and are hence considered "extras" or "external" modules. One of these modules is, in fact, repackaged here although published independently.
49
+
50
+ On of the external modules provides methods for estimating confidence intervals for proportions and for contrasts (differences) in proportions. This module improve is coded for conformance to the literature and to results from the corresponding modules in :code:`R`. Although written from scratch, the APIs implemented in the module included here are designed for consistency with the APIs in, :code:`statsmodels.stats.proportion` from the package, :code:`statsmodels` (https://pypi.org/project/statsmodels/). To access these directly:
51
+
52
+ .. code-block:: python
53
+
54
+ import mergeron.ext.proportions_tests as prci
55
+
56
+ Module :code:`mergeron.ext.xlsxw_helper` is useful for writing highly formatted output to spreadsheets with xlsx format. The class, :code:`mergeron.ext.xlsxw_helper.CFmt` and function, :code:`mergeron.ext.xlsxw_helper.array_to_sheet` are of particular interest, and can be accessed as :code:`xlh.CFmt` and :code:`xlh.array_to_sheet` with the following import:
57
+
58
+ .. code-block:: python
59
+
60
+ import mergeron.ext.xlsxw_helper as xlsxw_helper
61
+
62
+ A recent version of Paul Tol's python module, :code:`tol_colors.py`, which provides high-contrast color schemes for making displays with improved visibility for individuals with color-blindness, is redistributed within this package. Other than re-formatting and type annotation, the :code:`mergeron.ext.tol_colors` module is re-distributed as downloaded from, https://personal.sron.nl/~pault/data/tol_colors.py. The :code:`tol_colors.py` module is distributed under the Standard 3-clause BSD license. To access the :code:`mergeron.ext.tol_colors` module directly:
63
+
64
+ .. code-block:: python
65
+
66
+ import mergeron.ext.tol_colors as ptc
67
+
68
+ .. image:: https://img.shields.io/endpoint?url=https://python-poetry.org/badge/v0.json
69
+ :alt: Poetry
70
+ :target: https://python-poetry.org/
71
+
72
+ .. image:: https://img.shields.io/endpoint?url=https://raw.githubusercontent.com/astral-sh/ruff/main/assets/badge/v2.json
73
+ :alt: Ruff
74
+ :target: https://github.com/astral-sh/ruff
75
+
76
+ .. image:: https://www.mypy-lang.org/static/mypy_badge.svg
77
+ :alt: Checked with mypy
78
+ :target: https://mypy-lang.org/
79
+
80
+ .. image:: https://img.shields.io/badge/License-MIT-yellow.svg
81
+ :alt: License: MIT
82
+ :target: https://opensource.org/licenses/MIT
83
+
@@ -13,7 +13,7 @@ keywords = [
13
13
  "upward pricing pressure",
14
14
  "GUPPI",
15
15
  ]
16
- version = "2024.739091.2"
16
+ version = "2024.739097.2"
17
17
 
18
18
  # Classifiers list: https://pypi.org/classifiers/
19
19
  classifiers = [
@@ -37,7 +37,6 @@ aenum = "^3.1.15"
37
37
  attrs = ">=23.2"
38
38
  bs4 = ">=0.0.1"
39
39
  google-re2 = ">=1.1"
40
- icecream = ">=2.1.0"
41
40
  jinja2 = ">=3.1"
42
41
  joblib = ">=1.3"
43
42
  lxml = ">=5.0"
@@ -47,7 +46,6 @@ msgpack = ">=1.0"
47
46
  msgpack-numpy = ">=0.4"
48
47
  numpy = ">=1.26, <2.0"
49
48
  openpyxl = ">=3.1.2"
50
- pendulum = ">=3.0.0"
51
49
  python = "^3.12"
52
50
  requests = ">=2.31"
53
51
  scipy = ">=1.12"
@@ -63,10 +61,12 @@ poetry-plugin-export = "^1.8.0"
63
61
 
64
62
 
65
63
  [tool.poetry.group.dev.dependencies]
66
- semver = ">=3.0"
64
+ icecream = ">=2.1.0"
67
65
  mypy = ">=1.8"
66
+ pendulum = ">=3.0.0"
68
67
  ruff = ">=0.5"
69
68
  pytest = ">=8.0"
69
+ semver = ">=3.0"
70
70
  sphinx = ">=7.2"
71
71
  sphinx-autodoc-typehints = ">=2.0.0"
72
72
  sphinx-autoapi = ">=3.0"
@@ -2,16 +2,12 @@ from __future__ import annotations
2
2
 
3
3
  import enum
4
4
  from pathlib import Path
5
- from typing import Any
6
5
 
7
6
  import numpy as np
8
- import pendulum # type: ignore
9
- from icecream import argumentToString, ic, install # type: ignore
10
- from numpy.typing import NDArray
11
7
 
12
8
  _PKG_NAME: str = Path(__file__).parent.stem
13
9
 
14
- VERSION = "2024.739091.2"
10
+ VERSION = "2024.739097.2"
15
11
 
16
12
  __version__ = VERSION
17
13
 
@@ -28,19 +24,6 @@ if not DATA_DIR.is_dir():
28
24
  np.set_printoptions(precision=18)
29
25
 
30
26
 
31
- def _timestamper() -> str:
32
- return f"{pendulum.now().strftime("%F %T.%f")} |> "
33
-
34
-
35
- @argumentToString.register(np.ndarray) # type: ignore
36
- def _(_obj: NDArray[Any]) -> str:
37
- return f"ndarray, shape={_obj.shape}, dtype={_obj.dtype}"
38
-
39
-
40
- ic.configureOutput(prefix=_timestamper, includeContext=True)
41
- install()
42
-
43
-
44
27
  @enum.unique
45
28
  class RECConstants(enum.StrEnum):
46
29
  """Recapture rate - derivation methods."""
@@ -202,7 +202,7 @@ def mgn_data_resampler(
202
202
  Parameters
203
203
  ----------
204
204
  _sample_size
205
- Number of draws
205
+ Number of draws; if tuple, (number of draws, number of columns)
206
206
 
207
207
  seed_sequence
208
208
  SeedSequence for seeding random-number generator when results
@@ -22,7 +22,6 @@ import numpy as np
22
22
  import re2 as re # type: ignore
23
23
  import requests
24
24
  from bs4 import BeautifulSoup
25
- from icecream import ic # type: ignore
26
25
  from numpy.testing import assert_array_equal
27
26
  from numpy.typing import NDArray
28
27
 
@@ -345,7 +344,7 @@ def _construct_new_period_data(
345
344
  # _invdata_array_bld_enfcls < 0, _invdata_array_bld_enfcls, 0
346
345
  # )
347
346
  # if np.einsum('ij->', invdata_array_bld_tbc):
348
- # ic(
347
+ # print(
349
348
  # f"{_data_period}, {_table_no}, {_invdata_ind_group}:",
350
349
  # abs(np.einsum('ij->', invdata_array_bld_tbc))
351
350
  # )
@@ -551,7 +550,7 @@ def _parse_table_blocks(
551
550
  _invdata_evid_cond = "Unrestricted on additional evidence"
552
551
 
553
552
  else:
554
- # ic(_table_blocks)
553
+ # print(_table_blocks)
555
554
  _invdata_evid_cond = (
556
555
  _table_blocks[1][-3].strip()
557
556
  if _table_ser == 9
@@ -570,8 +569,8 @@ def _parse_table_blocks(
570
569
 
571
570
  _table_array = process_table_func(_table_blocks)
572
571
  if not isinstance(_table_array, np.ndarray) or _table_array.dtype != np.int64:
573
- ic(_table_num)
574
- ic(_table_blocks)
572
+ print(_table_num)
573
+ print(_table_blocks)
575
574
  raise ValueError
576
575
 
577
576
  _table_data = INVTableData(_invdata_ind_group, _invdata_evid_cond, _table_array)
@@ -11,6 +11,14 @@ This module is designed for producing formatted summary output. For
11
11
  writing bulk data to Excel, facilities provided in third-party packages
12
12
  such as `polars <https://pola.rs/>`_ likely provide better performance.
13
13
 
14
+ License
15
+ ========
16
+
17
+ Copyright 2017-2023 S. Murthy Kambhampaty
18
+ Licese: MIT
19
+ https://mit-license.org/
20
+
21
+
14
22
  """
15
23
 
16
24
  from __future__ import annotations
@@ -21,7 +21,7 @@ __version__ = VERSION
21
21
 
22
22
  EMPTY_ARRAY_DEFAULT = np.zeros(2)
23
23
  FCOUNT_WTS_DEFAULT = np.divide(
24
- (_nr := np.arange(1, 6)[::-1]), _nr.sum(), dtype=np.float64
24
+ (_nr := np.arange(1, 7)[::-1]), _nr.sum(), dtype=np.float64
25
25
  )
26
26
 
27
27
 
@@ -36,7 +36,7 @@ class PriceConstants(tuple[bool, str | None], enum.ReprEnum):
36
36
  ZERO = (False, None)
37
37
  NEG = (False, "negative share-correlation")
38
38
  POS = (False, "positive share-correlation")
39
- # TODO: CSY = (False, "market-wide cost-symmetry")
39
+ CSY = (False, "market-wide cost-symmetry")
40
40
 
41
41
 
42
42
  @enum.unique
@@ -59,7 +59,11 @@ class SHRConstants(enum.StrEnum):
59
59
  DIR_ASYM = "Asymmetric Dirichlet"
60
60
  """Share distribution for merging-firm shares has a higher peak share
61
61
 
62
- Shape parameter for merging-firm-share is 2.5, and 1.0 for all others.
62
+ By default, shape parameter for merging-firm-share is 2.5, and
63
+ 1.0 for all others. Defining, :attr:`mergeron.ShareSpec.dist_parms`
64
+ as a vector of shape parameters with length matching
65
+ that of :attr:`mergeron.ShareSpec.dist_parms` allows flexible specification
66
+ of Dirichlet-distributed share-data generation.
63
67
  """
64
68
 
65
69
  DIR_COND = "Conditional Dirichlet"
@@ -74,13 +78,24 @@ class SHRConstants(enum.StrEnum):
74
78
  class ShareSpec:
75
79
  """Market share specification
76
80
 
81
+ A key feature of market-share specification in this package is that
82
+ the draws represent markets with multiple different firm-counts.
83
+ Firm-counts are unspecified if the share distribution is
84
+ :attr:`mergeron.SHRConstants.UNI`, for Dirichlet-distributed market-shares,
85
+ the default specification is that firm-counts vary between
86
+ 2 and 7 firms with each value equally likely.
87
+
77
88
  Notes
78
89
  -----
79
- If recapture is determined "outside-in", market shares cannot have
80
- Uniform distribution.
90
+ If :attr:`mergeron.gen.ShareSpec.dist_type`:code:` == `:attr:`mergeron.gen.SHRConstants.UNI`,
91
+ then it is infeasible that
92
+ :attr:`mergeron.gen.ShareSpec.recapture_form`:code:` == `:attr:`mergeron.RECConstants.OUTIN`.
93
+ In other words, if firm-counts are unspecified, the recapture rate cannot be
94
+ estimated using outside good choice probabilities.
81
95
 
82
- If sample with varying firm counts is required, market shares must
83
- be specified as having a supported Dirichlet distribution.
96
+ For a sample with explicit firm counts, market shares must
97
+ be specified as having a supported Dirichlet distribution
98
+ (see :class:`mergeron.gen.SHRConstants`).
84
99
 
85
100
  """
86
101
 
@@ -446,7 +461,8 @@ class UPPTestRegime:
446
461
  default=UPPAggrSelector.MIN, validator=validators.instance_of(UPPAggrSelector)
447
462
  )
448
463
  divr_aggregator: UPPAggrSelector | None = field(
449
- default=None, validator=validators.instance_of((UPPAggrSelector, type(None)))
464
+ default=UPPAggrSelector.MIN,
465
+ validator=validators.instance_of((UPPAggrSelector, type(None))),
450
466
  )
451
467
 
452
468