33import pyfar as pf
44
55
6- def paris_formula (coefficients , incident_directions ):
6+ def paris_formula (coefficients , colatitude_rad , area_weights ):
77 r"""
88 Calculate the random-incidence coefficient
99 according to the Paris formula.
1010
11+ The Paris formula computes the random-incidence coefficient based on
12+ directional coefficients. It is valid for scattering and absorption
13+ coefficients and requires equally distributed incident directions
14+ to get a valid result.
15+
1116 The implementation follows the Equation 2.53 from [#]_ and is
1217 discretized as:
1318
1419 .. math::
15- c_{rand} = \sum_{\Omega_S} c(\Omega_S) \cdot |\Omega_S \cdot n| \cdot w
20+ c_{rand} = \sum_{\Omega_S} c(\Omega_S) \cdot \cos(\theta) \cdot w
1621
1722 with the `coefficients` :math:`c`, and the
1823 area weights :math:`w` from the `incident_directions`.
19- :math:`|\Omega_S \cdot n|` represent the cosine of the angle between the
24+ :math:`\theta` represents the angle between the
2025 surface normal and the incident direction.
2126
22- .. note::
23- The incident directions should be
24- equally distributed to get a valid result.
25-
2627 Parameters
2728 ----------
2829 coefficients : pyfar.FrequencyData
2930 coefficients for different incident directions. Its cshape
30- needs to be (..., n_incident_directions)
31- incident_directions : pyfar.Coordinates
32- Defines the incidence directions of each `coefficients` in a
33- Coordinates object. Its cshape needs to be (n_incident_directions). In
34- sperical coordinates the radii needs to be constant. The area weights must be
35- stored in ``ìncedent_directions.weights``.
31+ needs to be (..., n_incident_directions).
32+ colatitude_rad : pyfar.Coordinates
33+ Defines the angle between the surface normal and the sound
34+ incidence in radiant. Its cshape
35+ needs to be (n_incident_directions).
36+ area_weights : np.ndarray
37+ Area weights for each incident direction. Its cshape
38+ needs to be (n_incident_directions).
3639
3740 Returns
3841 -------
3942 random_coefficient : pyfar.FrequencyData
40- The random-incidence scattering coefficient.
43+ The random-incidence coefficient.
4144
4245 References
4346 ----------
@@ -46,20 +49,14 @@ def paris_formula(coefficients, incident_directions):
4649 """
4750 if not isinstance (coefficients , pf .FrequencyData ):
4851 raise ValueError ("coefficients has to be FrequencyData" )
49- if not isinstance (incident_directions , pf .Coordinates ):
50- raise ValueError ("incident_directions have to be Coordinates" )
51- if incident_directions .cshape [0 ] != coefficients .cshape [- 1 ]:
52+ if colatitude_rad .shape != area_weights .shape :
5253 raise ValueError (
53- "the last dimension of coefficients needs be same as "
54- "the incident_directions.cshape." )
54+ "colatitude_rad and area_weights need to have the same shape." )
5555
56- theta = incident_directions .colatitude
57- weight = np .cos (theta ) * incident_directions .weights
56+ theta = colatitude_rad
57+ weight = np .cos (theta ) * area_weights
58+ weight = weight [..., np .newaxis ]
5859 norm = np .sum (weight )
59- coefficients_freq = np .swapaxes (coefficients .freq , - 1 , - 2 )
60- random_coefficient = pf .FrequencyData (
61- np .sum (coefficients_freq * weight / norm , axis = - 1 ),
62- coefficients .frequencies ,
63- comment = 'random-incidence coefficient' ,
64- )
60+ random_coefficient = coefficients * weight / norm
61+ random_coefficient .freq = np .sum (random_coefficient .freq , axis = - 2 )
6562 return random_coefficient
0 commit comments