pygeodesy 24.9.9__py2.py3-none-any.whl → 24.9.29__py2.py3-none-any.whl

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.
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: PyGeodesy
3
- Version: 24.9.9
3
+ Version: 24.9.29
4
4
  Summary: Pure Python geodesy tools
5
5
  Home-page: https://GitHub.com/mrJean1/PyGeodesy
6
6
  Author: Jean M. Brouwers
@@ -8,7 +8,7 @@ Author-email: mrJean1@Gmail.com
8
8
  Maintainer: Jean M. Brouwers
9
9
  Maintainer-email: mrJean1@Gmail.com
10
10
  License: MIT
11
- Keywords: AER Albers altitude Andoyer annulus antipode area attitude Authalic auxiliary azimuth azimuthal azimuth-elevation-range bearing bank Barsky Barth beta bi-quadratic boolean cached Cagnoli cartesian Cassini Cassini-Soldner chord circle-intersections circumcenter circumcircle circumradius clip Cohen Cohen-Sutherland Collins composite conformal conic constants contact-triangle Cook Correia cosines-law coverage curvature cylindrical datum deprecation deficit development discrete distance Douglas earth east-north-up eccentricity ECEF elevation ellipsoid ellipsoidal-latitude-beta ellipsoidal-longitude-omega elliptic ENU EPSG equal-area equidistant equirectangular ETM ETRF Euclidean even-odd-rule ExactTM excess Farrell Farrell-Barth Field-Of-View flattening fma fmath footprint Forster Forster-Hormann-Popa Forsythe FOV fractional Frechet Fréchet frustum Fsum fused-multiply-add GARS geocentric GeoConvert GeodesicExact geodesy geodetic GeodSolve GeodTest geographiclib Geohash geoid geoidHeight GeoidHeights georef Girard gnomonic gons grades gradians Greiner Greiner-Hormann Hartzell Hausdorff Haversine heading height Heron Hodgman horizon Hormann Hubeny IDW incenter incirle infix_@_operator inradius intermediate interpolate intersect intersection intersection3d intersections IntersectTool Inverse-Distance-Weighting Isometric ITRF Jacobi Jacobi-Conformal Jarque-Bera Jekel Karney Krueger Krüger kurtosis Lambert latitude law-of-cosines least-squares Lesh L_Huilier LHuilier Liang Liang-Barsky linearize Line-Of-Sight LocalCartesian local-tangent-plane local-x-y-z longitude LOS loxodrome lstsq LTP lune LV03 LV95 mean memoize memoized Mercator Meeus MGRS nearest NED Niemeyer normalize Norrdine north-east-down numpy n-vector Nvector oblate omega orthographic orthometric-height OSGB OSGR overlap parallel parallel-of-latitude Parametric path-intersection perimeter Peucker Pierlot pitch plumb Point-Of-View polar Popa POV precision-cubic-root precision-hypotenuse precision-powers precision-running-summation precision-square-root precision-summation prolate Pseudo-Mercator PyGeodesy PyInstaller PyPy quartic radical radii radius Ramer Ramer-Douglas-Peucker Rectifying Reduced resect resection Rey-Jer Reumann Reumann-Witkam rhumb RhumbSolve running-linear-regression running-statistics running-stats running-summation scipy secant semi-perimeter sexagecimal simplify skewness Snellius Snellius-Pothenot Snyder Soddy Soddy-circles Soldner sphere sphere-intersections spherical-deficit spherical-excess spherical-triangle squared-quartic standard-deviation stereographic Sudano surface-area Sutherland Sutherland-Hodgman tangent-circles Terrestrial-Reference-Frame Thomas Tienstra tilt TMcoords TMExact toise transverse TransverseMercatorExact TRF triangle triangulate triaxial triaxial-ellipsoid trigonometry trilaterate trilaterate-2d trilaterate-3d TwoProduct TwoSum umbilic-point unit unroll UPS UTM UTM/UPS variance velocities Veness Vermeille viewing-frustum Vincenty Visvalingam Visvalingam-Whyatt volume volumetric Web-Mercator Welford WGRS WGS Whyatt Wildberger Witkam winding-number XYZ yaw You zenzi-cubic zenzi-quartic
11
+ Keywords: AER Albers altitude Andoyer annulus antipode area attitude Authalic auxiliary azimuth azimuthal azimuth-elevation-range bearing bank Barsky Barth beta bi-quadratic boolean cached Cagnoli cartesian Cassini Cassini-Soldner chord circle-intersections circumcenter circumcircle circumradius clip Cohen Cohen-Sutherland Collins composite conformal conic constants contact-triangle Cook Correia cosines-law coverage curvature cylindrical datum deprecation deficit development discrete distance Douglas earth east-north-up eccentricity ECEF elevation ellipsoid ellipsoidal-latitude-beta ellipsoidal-longitude-omega elliptic ENU EPSG equal-area equidistant equirectangular ETM ETRF Euclidean even-odd-rule ExactTM excess Farrell Farrell-Barth Field-Of-View flattening fma fmath footprint Forster Forster-Hormann-Popa Forsythe FOV fractional Frechet Fréchet frustum Fsum fused-multiply-add GARS geocentric GeoConvert GeodesicExact geodesy geodetic GeodSolve GeodTest geographiclib Geohash geoid geoidHeight GeoidHeights georef Girard gnomonic gons grades gradians Greiner Greiner-Hormann Hartzell Hausdorff Haversine heading height Heron Hodgman horizon Hormann Hubeny IDW incenter incirle infix_@_operator inradius intermediate interpolate intersect intersection intersection3d intersections IntersectTool Inverse-Distance-Weighting Isometric ITRF Jacobi Jacobi-Conformal Jarque-Bera Jekel Karney Krueger Krüger kurtosis Lambert latitude law-of-cosines least-squares Lesh L_Huilier LHuilier Liang Liang-Barsky linearize Line-Of-Sight LocalCartesian local-tangent-plane local-x-y-z longitude LOS loxodrome lstsq LTP lune LV03 LV95 mean memoize memoized Mercator Meeus MGRS nearest NED Niemeyer non-finite normalize Norrdine north-east-down numpy n-vector Nvector oblate omega orthographic orthometric-height OSGB OSGR overlap parallel parallel-of-latitude Parametric path-intersection perimeter Peucker Pierlot pitch plumb Point-Of-View polar Popa POV precision-cubic-root precision-hypotenuse precision-powers precision-running-summation precision-square-root precision-summation prolate Pseudo-Mercator PyGeodesy PyInstaller PyPy quartic radical radii radius Ramer Ramer-Douglas-Peucker Rectifying Reduced resect resection Rey-Jer Reumann Reumann-Witkam rhumb RhumbSolve running-linear-regression running-statistics running-stats running-summation scipy secant semi-perimeter sexagecimal simplify skewness Snellius Snellius-Pothenot Snyder Soddy Soddy-circles Soldner sphere sphere-intersections spherical-deficit spherical-excess spherical-triangle squared-quartic standard-deviation stereographic Sudano surface-area Sutherland Sutherland-Hodgman tangent-circles Terrestrial-Reference-Frame Thomas Tienstra tilt TMcoords TMExact toise transverse TransverseMercatorExact TRF triangle triangulate triaxial triaxial-ellipsoid trigonometry trilaterate trilaterate-2d trilaterate-3d TwoProduct TwoSum umbilic-point unit unroll UPS UTM UTM/UPS variance velocities Veness Vermeille viewing-frustum Vincenty Visvalingam Visvalingam-Whyatt volume volumetric Web-Mercator Welford WGRS WGS Whyatt Wildberger Witkam winding-number XYZ yaw You zenzi-cubic zenzi-quartic
12
12
  Classifier: Development Status :: 5 - Production/Stable
13
13
  Classifier: Environment :: Console
14
14
  Classifier: Intended Audience :: Developers
@@ -115,7 +115,7 @@ line: ``epydoc --html --no-private --no-source --name=PyGeodesy --url=... -v pyg
115
115
  Tests
116
116
  =====
117
117
 
118
- The tests ran with Python 3.13.0rc1, 3.12.5 (with geographiclib_ 2.0, numpy_ 2.1.0, scipy_ 1.14.1,
118
+ The tests ran with Python 3.13.0rc2, 3.12.6 (with geographiclib_ 2.0, numpy_ 2.1.0, scipy_ 1.14.1,
119
119
  GeodSolve_ 2.3, IntersectTool_ 2.3 and RhumbSolve_ 2.3), 3.11.5 (with geographiclib_ 2.0, numpy_
120
120
  1.24.2 and scipy_ 1.10.1), Python 3.10.8 (with geographiclib_ 2.0, numpy_ 1.23.3, scipy_ 1.9.1,
121
121
  GeoConvert_ 2.3, GeodSolve_ 2.3), Python 3.9.6 and Python 2.7.18 (with geographiclib_ 1.50, numpy_
@@ -126,13 +126,13 @@ All tests ran with and without ``lazy import`` for Python 3 and with command lin
126
126
  and env variable ``PYGEODESY_WARNINGS=on`` for all Python versions. The results of those tests are
127
127
  included in the distribution files.
128
128
 
129
- Python 3.13.0rc1, 3.12.5, 3.11.5 and 3.10.8 run on Apple M1 Silicon (``arm64``), *natively*. Python 2.7.18
129
+ Python 3.13.0rc2, 3.12.6, 3.11.5 and 3.10.8 run on Apple M1 Silicon (``arm64``), *natively*. Python 2.7.18
130
130
  runs on Intel (``x86_64``) or Intel *emulation* (\"``arm64_x86_64``\", see function `pygeodesy.machine`_).
131
131
 
132
- Test coverage has been measured with coverage_ 7.6.0 using Python 3.12.5, 3.11.5 and 3.10.8. The complete
132
+ Test coverage has been measured with coverage_ 7.6.0 using Python 3.12.6, 3.11.5 and 3.10.8. The complete
133
133
  coverage report in HTML and a PDF summary are included in the distribution files.
134
134
 
135
- The tests also ran with Python 3.12.5 (and geographiclib_ 2.0) on `Debian 12`_ in 64-bit only and with
135
+ The tests also ran with Python 3.12.6 (and geographiclib_ 2.0) on `Debian 12`_ in 64-bit only and with
136
136
  Python 3.12.3 (and geographiclib_ 2.0) on `Windows 2019Server`_ in 64-bit only and with Python 2.7.18
137
137
  (and with geographiclib_ 1.52) on `Windows 10`_ in 64- and 32-bit.
138
138
 
@@ -160,7 +160,7 @@ and McCabe_ using Python 2.7.18 and with Flake8_ using Python 3.11.5, both in 64
160
160
 
161
161
  For a summary of all *Karney*-based functionality in ``pygeodesy``, see module karney_.
162
162
 
163
- *Last updated: Sep 09, 2024.*
163
+ *Last updated: Sep 29, 2024.*
164
164
 
165
165
  License
166
166
  =======
@@ -1,20 +1,20 @@
1
1
  pygeodesy/LICENSE,sha256=YfgAiyxOwY6P9Kkb1_5XN81nueTLrpb3Ffkv3EuPgFU,1144
2
- pygeodesy/__init__.py,sha256=ohpvlHHdgFq_uc-u1gq7deCyTlzB_nq-Lc8tZGWN-Go,42225
2
+ pygeodesy/__init__.py,sha256=MPSm_QycgTQamFcQG7hsKLKULgZK4MscaLnEOmrqUq0,42475
3
3
  pygeodesy/__main__.py,sha256=OupAiDFT_RXFw1Lh6C8bVG9NaonV_Wy6jibN_hA4aJg,5442
4
4
  pygeodesy/albers.py,sha256=JXqeWAteV2N601e5R-D7bCsa8qAYv3oWm7M3R4uszXM,31078
5
5
  pygeodesy/azimuthal.py,sha256=erI5DTM0-Nr5YC2LnBTVNbUKlrnnXJUwKe0SCQ7-Soc,50223
6
- pygeodesy/basics.py,sha256=5fuWL_azUd6DxSGUwB4RJERH_ZrBB0vVqDc9wvxpIHo,30116
7
- pygeodesy/booleans.py,sha256=mWNdmk5cYfcH3v0sEpU3Aw5sFLp_dq5mXJodzenOEm0,73506
6
+ pygeodesy/basics.py,sha256=JPANq5maTBqd4PhHIO4TLCfl9SG0D0n6OiUF421p1bQ,30163
7
+ pygeodesy/booleans.py,sha256=gEh1bWdHEoSv-4yp0M9JE73xa4DLwLllgKC9d0mNLwM,73460
8
8
  pygeodesy/cartesianBase.py,sha256=jzPJR4_3Yp5jmK7A5inGOXskDebs7YMdjQzINHjzkP8,46935
9
- pygeodesy/clipy.py,sha256=3ysIEWQ89HjvLnSlZm0nZAt9EN5AQxIs1sLLM8yF9zM,27675
10
- pygeodesy/constants.py,sha256=vW6CWRa62hHJqmKhlPxI4Eu-cbLhoUYWYTd9ctfFo-8,19240
9
+ pygeodesy/clipy.py,sha256=hzI6IutTRkbssjPPgAjXv9OcgCIIZchjnMWaHin4YAU,27728
10
+ pygeodesy/constants.py,sha256=E3ANfteZK05I89wbGP4Noxms0pT2TKBOyaVSv8jmlxg,19673
11
11
  pygeodesy/css.py,sha256=rPr5EcGm_blVt72h-851ytpVxdPhx1MEqqGs3Ppx3eI,25651
12
12
  pygeodesy/datums.py,sha256=-m9-cvUVOaJ92eeFgc3O54lel3WqnVYcS7o6WCXkNyw,34043
13
13
  pygeodesy/dms.py,sha256=QxiRtyc8QSiW-egm6Mrcrgmi_deWz3YnYwIm82JS4TU,44443
14
14
  pygeodesy/ecef.py,sha256=_yy_TIUGsXmEZ7aRcmchbJwTp7x__edx6EPiS3Xznes,59587
15
15
  pygeodesy/elevations.py,sha256=4FuVcVNb_D09gmcvUlck344N4f7Jms76SIRrdutvKjk,10801
16
16
  pygeodesy/ellipsoidalBase.py,sha256=IDu0-cKGhkCk3Aj16DJXt2gxjGYsFcjSTrvwG5GbATs,55385
17
- pygeodesy/ellipsoidalBaseDI.py,sha256=OxbSBntV9xiOgsb-0un0cUYIVoPiIiH-lt3baBkbaS8,38400
17
+ pygeodesy/ellipsoidalBaseDI.py,sha256=wsUcdVdp1Tcs8IOS6bM773tAShIOqt_yscRFU2oiehI,38397
18
18
  pygeodesy/ellipsoidalExact.py,sha256=wmIGgZyd0cvjswP4KOeDuEcuagjwQQRRq1cmseRoD-Q,16946
19
19
  pygeodesy/ellipsoidalGeodSolve.py,sha256=fAT4b3HXkM6i1W_C0rb4vbSxZqr4c6rS7PIvGF2ad7s,16666
20
20
  pygeodesy/ellipsoidalKarney.py,sha256=qvJa8kZ4SgaRR2UbjtkcRxw_CRbwhXoUT4Dn_6DJ6Ag,18721
@@ -23,13 +23,13 @@ pygeodesy/ellipsoidalVincenty.py,sha256=hSQ7s6QGDJSsrZvP7KwM1Q4wJz0YjyFjODF6XPGZ
23
23
  pygeodesy/ellipsoids.py,sha256=i7piclEb17hYt5wqL7Q0p5qLuRVvz3yonUSUcvmiozc,108005
24
24
  pygeodesy/elliptic.py,sha256=M30EjB1Il_5Y8E94rN5hz4zPhYBQNoCo5Lj0TvCkiRE,45010
25
25
  pygeodesy/epsg.py,sha256=Vq_M1g7Z0x5Noqsmt6OCQkPdYJj4jpWObtixL5pAjDA,8220
26
- pygeodesy/errors.py,sha256=-UnQ1GhkiTR6uBd0z0vd_pFEmjWXlOESRDwMdxY_JD0,30605
26
+ pygeodesy/errors.py,sha256=w7aUnWFFWavu1TiMyAuxA2bAHYOZltzYqauurU8pmLY,31907
27
27
  pygeodesy/etm.py,sha256=G6dtN1LQAoft5mcUoxVgxHPnl9s8NBsXl-IlS8WP7jo,45328
28
- pygeodesy/fmath.py,sha256=7Bokavxcu4oFGMKHCn4JxbETDisbBkWJqJx-KiCtHPM,34374
29
- pygeodesy/formy.py,sha256=PrAlrSASKIXeFvawueyo7kRC-UJJSEQR3APhirHqhtE,75032
28
+ pygeodesy/fmath.py,sha256=44yyf6shurGxFxFIj_huTk0cnRaMYYEgouFNdPrmZI0,35427
29
+ pygeodesy/formy.py,sha256=FvbkYhJ-iIOFR-IOImwm0I_dgXM9CfnWrJK_IvBX0SU,75082
30
30
  pygeodesy/frechet.py,sha256=F6TYbOEYSOFcll6nvp4GhqafUWXh1umAKb1QaMYQtuM,34372
31
- pygeodesy/fstats.py,sha256=4eIhzSCMnn-2nVP3Q-5cCWCI-rvH0CE-zkk9hp3Pvn8,28642
32
- pygeodesy/fsums.py,sha256=Zk65c445gAz7Ld_iXL1zZ3ZtkA_gM2edDOf9nJSEnXE,87433
31
+ pygeodesy/fstats.py,sha256=r-RKXOwq2vcwEVrscKyMz0jgeyUFPD4izReKuNbxwoE,28548
32
+ pygeodesy/fsums.py,sha256=GgHfZMCexk_q85m0kH4jhkeMnHnoPQ7X334Jzj3t8QM,101835
33
33
  pygeodesy/gars.py,sha256=KRlyZUv1euEl7ZkDYSZG913GAfFMRG2m2hp37ObYY_Y,11829
34
34
  pygeodesy/geodesici.py,sha256=I9e7saiO5lRodOXJk5DSQxladVcGfT0FR6KJSJVCw7Y,75015
35
35
  pygeodesy/geodesicw.py,sha256=oEs96Epw839BH3rVpxVdpXuQRBudbOftUsSBUid8fcc,28710
@@ -41,10 +41,10 @@ pygeodesy/heights.py,sha256=Gv3b1xC7I0tBvTO-DdmWVW8A3ZV3RKxY3jveUUZso38,42909
41
41
  pygeodesy/internals.py,sha256=TSJueckcn6dQddZUhLR0Vf9XN-Whm85IYmSvhVZbB_s,22550
42
42
  pygeodesy/interns.py,sha256=XvNyWODsUd8_vBLX9XLmcU9Bq97L0nahhF-gvLivzKA,23278
43
43
  pygeodesy/iters.py,sha256=xPH0ytomvJeKHu717Fjzi3QbRrEikO6n7vqkY_IDz1k,20311
44
- pygeodesy/karney.py,sha256=2G5Y9FvZlb8cTrDHtHF71n3gxCvGLxlWUgVwXGmAnjA,39033
44
+ pygeodesy/karney.py,sha256=ZkZhbsieGnr2cAIXjzmK-9OJdh72Hjp6Hya1wIoVP3c,38913
45
45
  pygeodesy/ktm.py,sha256=eUWYKhoPou1AiWiNz-xI8eDr-q-RvKDY6newAmYP26Q,27239
46
46
  pygeodesy/latlonBase.py,sha256=kCK6IcVg4oeGPYkIU0rgKbZLCRo36wC9NtY5OKBlpeQ,79106
47
- pygeodesy/lazily.py,sha256=jIfuqXPh-Gvg4H2XeGgbKoOGuc49SR_sMVMoBEVq4LQ,47370
47
+ pygeodesy/lazily.py,sha256=NpWnTIAOkIxMorgUMvyR7d3D65-55DqaU98eBnwxcrQ,47411
48
48
  pygeodesy/lcc.py,sha256=oDooTzFHnqsMtSKmmmfEbypHpdlPltfo7Mt0pAO4-_A,25669
49
49
  pygeodesy/ltp.py,sha256=ZMdfJHLKeDHSoymmjWfoAZTtrdoADf0O6WccRf53L2w,50745
50
50
  pygeodesy/ltpTuples.py,sha256=oNTxtjxmHveMDQvPdQCHl-JzSJJGb1jFRrF8SEG_Ojw,58480
@@ -53,15 +53,15 @@ pygeodesy/named.py,sha256=-uqZk54BC4rFtuVh4LwfWty704DVPLEIwI1EzpNImIg,52350
53
53
  pygeodesy/namedTuples.py,sha256=e0rV1Zb2tbx8fztXcSkUFsRTmZtye8B5i_Hi4vBUndU,28758
54
54
  pygeodesy/nvectorBase.py,sha256=rClYu26Bof9DsM1F60i0eccktNo8xYA_vkThwoY7N4o,28644
55
55
  pygeodesy/osgr.py,sha256=3Qon_oWuVrIb1vYnd3ae3L5MDkjp_tngyVdiYHuL4to,30821
56
- pygeodesy/points.py,sha256=e8ri5Pu5snpN4P6pPbGxmW_yx4-ApD9mOBuR0REoflA,64409
56
+ pygeodesy/points.py,sha256=vtPQdL2kLOenIrpOdGjOYrUWsav3I1JXQEJugMv46eY,64383
57
57
  pygeodesy/props.py,sha256=3BIkcaEDwyhSMJle6ufBaji0R0FrD64G3nuR4tPsnrU,23819
58
- pygeodesy/resections.py,sha256=fFthuI9EoO4WdY25Y_rCDN56gz2mPFsUypR3oGlh8Ks,43556
58
+ pygeodesy/resections.py,sha256=IrPHAHbF9JdBgAVd9LMgXoPgPFRkY8j1G7p0P8y8pdc,43543
59
59
  pygeodesy/simplify.py,sha256=vkOtO478sOjZHZBuSFvCaRh72qSDQuzXLQpMK1LKyYI,25232
60
60
  pygeodesy/solveBase.py,sha256=oI_-FFjSPI1_yQ598hF6HFKUa4tLsAfbnWtKoQ-TJgE,19206
61
61
  pygeodesy/sphericalBase.py,sha256=bDVuArfePzqcothiTTkyisUGrMDTallXKROjihotcn8,32239
62
- pygeodesy/sphericalNvector.py,sha256=MiWcCy5CdvXsCa3963GeUMEnSYGhBiXzkoAEX_tGX4Q,56952
63
- pygeodesy/sphericalTrigonometry.py,sha256=F84lPOSLj4Z2-f8xMjpqvTISuBpsjFwdF8fkuaEi5Hs,64077
64
- pygeodesy/streprs.py,sha256=1szfCzFlVgsyJ0H_QFGtzyMfOJpyIZNfj34qvWNACM4,23041
62
+ pygeodesy/sphericalNvector.py,sha256=Ip0jPv-MXBoHf3f-uXitGqiMz2xynDtE15OSJEl268Q,56913
63
+ pygeodesy/sphericalTrigonometry.py,sha256=cfXuJaJJ6jrJZxQ5anFHhz3ZbgkAB7aiMfuyMtJXqsE,64064
64
+ pygeodesy/streprs.py,sha256=4aME8X-_9SS4VESootFOoK96aHjpwq3cKNTZ5u0q_nI,23342
65
65
  pygeodesy/trf.py,sha256=CRFHmu0lFNtc41fddXavEkHmgnTFWEqR4RTFodcFKsw,119022
66
66
  pygeodesy/triaxials.py,sha256=a9vdXmSqUXOneL0WpLriEFwNMW9EB6MpVbKYXuw_wi8,62562
67
67
  pygeodesy/units.py,sha256=gHN-uzsOwIYjyhtWs0th0VHNY-fOiUiZo9G1cZi0oXg,35272
@@ -87,12 +87,12 @@ pygeodesy/auxilats/auxDLat.py,sha256=3sq7Wc-ykpVbldNh10IZ3tIlJ7DcQFDlmZ4nOhJEgo0
87
87
  pygeodesy/auxilats/auxDST.py,sha256=BSHR0M3hQBR1KjF_BUJHrNzGXr2PblYXUQsMD5L1Kcc,10468
88
88
  pygeodesy/auxilats/auxLat.py,sha256=7uxe7mtkY-9uSI3z2wmUNBqzCKyFujIpJU1v-8yDgds,31934
89
89
  pygeodesy/auxilats/auxily.py,sha256=X1y4_qC40Th7CgmZILqoQCLAUQoyORcR5W-bN4X0W4I,7882
90
- pygeodesy/deprecated/__init__.py,sha256=cBYqbh5Njkd5SnaJDaMUP6PL66HfLWii_JoLjnKfnP4,2815
90
+ pygeodesy/deprecated/__init__.py,sha256=jSwmipBzyIOYIQhiZxZwsIQlqMXPfNaPfVpppBu7zkw,2815
91
91
  pygeodesy/deprecated/bases.py,sha256=nxUtxscAg5cb7HEzTSmPJFafLc9Ad2SL5ovwkYaU5z8,1655
92
92
  pygeodesy/deprecated/classes.py,sha256=gktUr5qYXCm8ztH6lfzFgaHKqMiw1tHc1Vw6i6DEvNA,12377
93
93
  pygeodesy/deprecated/consterns.py,sha256=W-rQiw443_zCFEUzjCGykGND-i5P_ghEIyJUSGg7-Nc,1908
94
94
  pygeodesy/deprecated/datum.py,sha256=s8Hke053RucP5ACvg3gdX8weQfGM0x59pQyHpY11eOs,1875
95
- pygeodesy/deprecated/functions.py,sha256=EZMZe9WGkcbwmLDoWO2xKJyFlUkWAAMxmlbtCLa28lM,13866
95
+ pygeodesy/deprecated/functions.py,sha256=-spa_5k7yRWGd7s4UBObzf9QpAM0o-tgP4S0wX876JY,14122
96
96
  pygeodesy/deprecated/nvector.py,sha256=_dZf84RdmPr7e7i8Yi683R-8Mqn0ipTqIsDhNl29hGo,2117
97
97
  pygeodesy/deprecated/rhumbBase.py,sha256=d7YKW--dnRpobB2CSvhFsntWF0B5-HYJqID2pv5lD5k,1375
98
98
  pygeodesy/deprecated/rhumbaux.py,sha256=n29xazYMbVG4MJkLjAGu8B88bbcFF5xnvuj9xSxjfIk,1428
@@ -112,7 +112,7 @@ pygeodesy/rhumb/aux_.py,sha256=XN0zlNwhU525NdcHko-G_Igvc7-mzXbT7ypcVIt5ADw,16048
112
112
  pygeodesy/rhumb/bases.py,sha256=awpP60K6EOzS753oXM-h9S6paS6FwoCnco8Zt8n81jY,54162
113
113
  pygeodesy/rhumb/ekx.py,sha256=JsmdCatWKqsffF8jCh4HDu5IKt_kHq1qUdmP1LMuofY,24044
114
114
  pygeodesy/rhumb/solve.py,sha256=d4RujlW8B7BFAHlrwfj2Bup-uXZZTpgKWgI2JJBqUGc,24059
115
- PyGeodesy-24.9.9.dist-info/METADATA,sha256=NZ7vpJ3lZq-5fmen4MR9YO3yRCcEuJN8zhpO8QtbKe0,19876
116
- PyGeodesy-24.9.9.dist-info/WHEEL,sha256=fS9sRbCBHs7VFcwJLnLXN1MZRR0_TVTxvXKzOnaSFs8,110
117
- PyGeodesy-24.9.9.dist-info/top_level.txt,sha256=cEQPatCXzKZqrivpULC5V5fuy9_V_bAwaP_gUGid7pQ,10
118
- PyGeodesy-24.9.9.dist-info/RECORD,,
115
+ PyGeodesy-24.9.29.dist-info/METADATA,sha256=bw_d3WzsZrHR7el08s2UwYG_Irc0KKwlN3h_dGtgZDY,19888
116
+ PyGeodesy-24.9.29.dist-info/WHEEL,sha256=fS9sRbCBHs7VFcwJLnLXN1MZRR0_TVTxvXKzOnaSFs8,110
117
+ PyGeodesy-24.9.29.dist-info/top_level.txt,sha256=cEQPatCXzKZqrivpULC5V5fuy9_V_bAwaP_gUGid7pQ,10
118
+ PyGeodesy-24.9.29.dist-info/RECORD,,
pygeodesy/__init__.py CHANGED
@@ -122,7 +122,7 @@ C{epydoc --html --no-private --no-source --name=PyGeodesy --url=... -v pygeodesy
122
122
  Tests
123
123
  =====
124
124
 
125
- The tests ran with Python 3.13.0rc1, Python 3.12.5 (with U{geographiclib<https://PyPI.org/project/geographiclib>} 2.0,
125
+ The tests ran with Python 3.13.0rc2, Python 3.12.6 (with U{geographiclib<https://PyPI.org/project/geographiclib>} 2.0,
126
126
  U{numpy<https://PyPI.org/project/numpy>} 2.1.0, U{scipy<https://PyPI.org/project/scipy>} 1.14.1,
127
127
  U{GeodSolve<https://GeographicLib.SourceForge.io/C++/doc/utilities.html>} 2.3,
128
128
  U{IntersectTool<https://GeographicLib.SourceForge.io/C++/doc/utilities.html>} 2.3 and
@@ -144,13 +144,13 @@ All tests ran with and without C{lazy import} for Python 3 and with command line
144
144
  env variable C{PYGEODESY_WARNINGS=on} for all Python versions. The results of those tests are included in
145
145
  the distribution files.
146
146
 
147
- Test coverage has been measured with U{coverage<https://PyPI.org/project/coverage>} 7.6.0 using Python 3.12.5,
147
+ Test coverage has been measured with U{coverage<https://PyPI.org/project/coverage>} 7.6.0 using Python 3.12.6,
148
148
  3.11.5 and 3.10.8. The complete coverage report in HTML and a PDF summary are included in the distribution files.
149
149
 
150
- Python 3.13.0rc1, 3.12.5, 3.11.5 and 3.10.8 run on Apple M1 Silicon (C{arm64}), I{natively}. Python 2.7.18 runs on
150
+ Python 3.13.0rc2, 3.12.6, 3.11.5 and 3.10.8 run on Apple M1 Silicon (C{arm64}), I{natively}. Python 2.7.18 runs on
151
151
  Intel (C{x86_64}) or Intel I{emulation} ("C{arm64_x86_64}", see function L{machine<pygeodesy.machine>}).
152
152
 
153
- The tests also ran with Python 3.12.5 (and U{geographiclib<https://PyPI.org/project/geographiclib>} 2.0) on U{Debian
153
+ The tests also ran with Python 3.12.6 (and U{geographiclib<https://PyPI.org/project/geographiclib>} 2.0) on U{Debian
154
154
  12<https://Cirrus-CI.com/github/mrJean1/PyGeodesy/master>} in 64-bit only, with Python 3.12.3 (and
155
155
  U{geographiclib<https://PyPI.org/project/geographiclib>} 2.0) on U{Windows
156
156
  2019Server<https://CI.AppVeyor.com/project/mrJean1/pygeodesy>} in 64-bit only and with Python 2.7.18 (and
@@ -199,6 +199,8 @@ The following environment variables are observed by C{PyGeodesy}:
199
199
 
200
200
  - C{PYGEODESY_EXCEPTION_CHAINING} - see module L{errors<pygeodesy.errors>}.
201
201
  - C{PYGEODESY_FMT_FORM} - see module L{dms<pygeodesy.dms>}.
202
+ - C{PYGEODESY_FSUM_F2PRODUCT} - see module L{fsums<pygeodesy.fsums>} and method L{f2product<pygeodesy.Fsum.f2product>}.
203
+ - C{PYGEODESY_FSUM_NONFINITES} - see module L{fsums<pygeodesy.fsums>} and function L{nonfiniterrors<pygeodesy.nonfiniterrors>}.
202
204
  - C{PYGEODESY_FSUM_RESIDUAL} - see module L{fsums<pygeodesy.fsums>} and class L{Fsum<pygeodesy.Fsum>}.
203
205
  - C{PYGEODESY_GEOCONVERT} - see module L{mgrs<pygeodesy.mgrs>}.
204
206
  - C{PYGEODESY_GEODSOLVE} - see module L{geodsolve<pygeodesy.geodsolve>}.
@@ -595,7 +597,7 @@ else:
595
597
 
596
598
  from pygeodesy.internals import _version2, _DOT_ # PYCHOK import
597
599
  # from pygeodesy.interns import _DOT_ # from .internals
598
- __version__ = '24.09.09'
600
+ __version__ = '24.09.29'
599
601
  # see setup.py for similar logic
600
602
  version = _DOT_(*_version2(__version__, n=3))
601
603
 
pygeodesy/basics.py CHANGED
@@ -19,6 +19,7 @@ del division
19
19
  from pygeodesy.errors import _AttributeError, _ImportError, _NotImplementedError, \
20
20
  _TypeError, _TypesError, _ValueError, _xAssertionError, \
21
21
  _xkwds_get1
22
+ # from pygeodesy.fsums import _isFsum_2Tuple # _MODS
22
23
  from pygeodesy.internals import _0_0, _enquote, _passarg, _version_info
23
24
  from pygeodesy.interns import MISSING, NN, _1_, _by_, _COMMA_, _DOT_, _DEPRECATED_, \
24
25
  _ELLIPSIS4_, _EQUAL_, _in_, _invalid_, _N_A_, _not_, \
@@ -37,7 +38,7 @@ from math import copysign as _copysign
37
38
  import inspect as _inspect
38
39
 
39
40
  __all__ = _ALL_LAZY.basics
40
- __version__ = '24.09.02'
41
+ __version__ = '24.09.28'
41
42
 
42
43
  _below_ = 'below'
43
44
  _list_tuple_types = (list, tuple)
@@ -119,7 +120,7 @@ def _args_kwds_count2(func, exelf=True):
119
120
  @kwarg exelf: If C{True}, exclude C{self} in the C{args}
120
121
  of a method (C{bool}).
121
122
  '''
122
- try:
123
+ try: # PYCHOK no cover
123
124
  a = k = 0
124
125
  for _, p in _inspect.signature(func).parameters.items():
125
126
  if p.kind is p.POSITIONAL_OR_KEYWORD:
@@ -150,7 +151,7 @@ def _args_kwds_names(func, splast=False):
150
151
  args_kwds = _inspect.signature(func).parameters.keys()
151
152
  except AttributeError: # .signature new Python 3+
152
153
  args_kwds = _inspect.getargspec(func).args
153
- if splast and args_kwds:
154
+ if splast and args_kwds: # PYCHOK no cover
154
155
  args_kwds = list(args_kwds)
155
156
  t = args_kwds[-1:]
156
157
  if t:
@@ -460,18 +461,16 @@ def isscalar(obj, both=False):
460
461
  '''Is B{C{obj}}ect an C{int} or integer C{float} value?
461
462
 
462
463
  @arg obj: The object (any C{type}).
463
- @kwarg both: If C{True}, check L{Fsum<Fsum.residual>}.
464
+ @kwarg both: If C{True}, check L{Fsum} and L{Fsum2Tuple}
465
+ residuals.
464
466
 
465
- @return: C{True} if C{int}, C{float} or L{Fsum} with
466
- zero residual, C{False} otherwise.
467
+ @return: C{True} if C{int}, C{float} or C{Fsum/-2Tuple}
468
+ with zero residual, C{False} otherwise.
467
469
  '''
468
470
  if isinstance(obj, _Scalars):
469
- return not isbool(obj)
470
- elif both: # and isinstance(obj, Fsum)
471
- try:
472
- return bool(obj.residual == 0)
473
- except (AttributeError, TypeError):
474
- pass # XXX float(int(obj)) == obj?
471
+ return not isbool(obj) # exclude bool
472
+ elif both and _MODS.fsums._isFsum_2Tuple(obj):
473
+ return bool(obj.residual == 0)
475
474
  return False
476
475
 
477
476
 
pygeodesy/booleans.py CHANGED
@@ -43,7 +43,7 @@ from pygeodesy.utily import fabs, _unrollon, _Wrap
43
43
  # from math import fabs # from .utily
44
44
 
45
45
  __all__ = _ALL_LAZY.booleans
46
- __version__ = '24.08.30'
46
+ __version__ = '24.09.28'
47
47
 
48
48
  _0_EPS = EPS # near-zero, positive
49
49
  _EPS_0 = -EPS # near-zero, negative
@@ -1117,7 +1117,7 @@ class _CompositeBase(_Named):
1117
1117
 
1118
1118
  def _sum1(self, _a_p, *args, **kwds): # in .karney, .points
1119
1119
  # Sum the area or perimeter of all clips
1120
- return _MODS.fsums.fsum1((_a_p(c, *args, **kwds) for c in self._clips), floats=True)
1120
+ return _MODS.fsums.fsum1((_a_p(c, *args, **kwds) for c in self._clips))
1121
1121
 
1122
1122
  def _sum2(self, LL, _a_p, *args, **kwds): # in .sphericalNvector, -Trigonometry
1123
1123
  # Sum the area or perimeter of all clips
@@ -1127,7 +1127,7 @@ class _CompositeBase(_Named):
1127
1127
  for v in clip:
1128
1128
  yield _LL(v.lat, v.lon) # datum=Sphere
1129
1129
 
1130
- return _MODS.fsums.fsum1((_a_p(_lls(c), *args, **kwds) for c in self._clips), floats=True)
1130
+ return _MODS.fsums.fsum1((_a_p(_lls(c), *args, **kwds) for c in self._clips))
1131
1131
 
1132
1132
  def toLatLon(self, LatLon=None, closed=False, **LatLon_kwds):
1133
1133
  '''Yield all (non-duplicate) points and intersections
@@ -1187,7 +1187,7 @@ class _CompositeFHP(_CompositeBase):
1187
1187
  n, b = v, v._label
1188
1188
  if b in L.RIGHT_LEFT_ON: # next chain
1189
1189
  while True:
1190
- n._label = None # n.__dict__.pop('_label')
1190
+ n._label = None # _xkwds_pop(n.__dict__, _label=None)
1191
1191
  n = n._next
1192
1192
  if n is v or n._label is not L.ON_ON: # n._label and ...
1193
1193
  break
@@ -1614,9 +1614,8 @@ class _EdgeGH(object):
1614
1614
  return a, fabs(d)
1615
1615
 
1616
1616
  def _Error(self, n, *args, **kwds): # PYCHOK no cover
1617
- t = unstr(_EdgeGH.__name__, self._s1, self._s2)
1618
- t = _DOT_(t, _EdgeGH._intersect4.__name__)
1619
- t = unstr(t, *args, **kwds)
1617
+ t = _DOT_(unstr(_EdgeGH, self._s1, self._s2),
1618
+ unstr(_EdgeGH._intersect4, *args, **kwds))
1620
1619
  return ClipError(_case_, n, txt=t)
1621
1620
 
1622
1621
  @Property_RO
pygeodesy/clipy.py CHANGED
@@ -15,22 +15,22 @@ from __future__ import division as _; del _ # PYCHOK semicolon
15
15
  # from pygeodesy.basics import len2 # from .fmath
16
16
  from pygeodesy.constants import EPS, _0_0, _1_0
17
17
  from pygeodesy.errors import _AssertionError, ClipError, PointsError
18
- from pygeodesy.fmath import fabs, len2
19
- from pygeodesy.fsums import fsumf_, Property_RO
18
+ from pygeodesy.fmath import fabs, len2, Fsum
19
+ # from pygeodesy.fsums import Fsum # from .fmath
20
20
  from pygeodesy.interns import NN, _clipid_, _convex_, _DOT_, _end_, _few_, \
21
21
  _fi_, _height_, _i_, _invalid_, _j_, _lat_, \
22
22
  _lon_, _near_, _not_, _points_, _start_, _too_
23
23
  from pygeodesy.iters import _imdex2, points2
24
24
  from pygeodesy.lazily import _ALL_LAZY, _ALL_MODS as _MODS
25
- from pygeodesy.named import _Named, _NamedTuple, _Pass
25
+ from pygeodesy.named import _Named, _NamedTuple, _Pass, Property_RO
26
26
  from pygeodesy.points import areaOf, boundsOf, isconvex_, LatLon_
27
- # from pygeodesy.props import Property_RO # from .fsums
27
+ # from pygeodesy.props import Property_RO # from .named
28
28
  from pygeodesy.units import Bool, FIx, HeightX, Lat, Lon, Number_
29
29
 
30
30
  # from math import fabs # from .fmath
31
31
 
32
32
  __all__ = _ALL_LAZY.clipy
33
- __version__ = '23.05.18'
33
+ __version__ = '23.09.20'
34
34
 
35
35
  _fj_ = 'fj'
36
36
  _original_ = 'original'
@@ -576,10 +576,10 @@ class _SH(_Named):
576
576
  x, dx = p1.lon, self._dx
577
577
  fy = float(p2.lat - y)
578
578
  fx = float(p2.lon - x)
579
- d = fy * dx - fx * dy
579
+ d = fy * dx - fx * dy # fdot((fx, fy), dx, -dy)
580
580
  if fabs(d) < EPS: # PYCHOK no cover
581
581
  raise _AssertionError(self._DOT_(self.intersect.__name__))
582
- d = fsumf_(self._xy, -y * dx, x * dy) / d
582
+ d = Fsum(self._xy, -y * dx, x * dy).fover(d)
583
583
  y += d * fy
584
584
  x += d * fx
585
585
  return _SHlli(y, x, p1.classof, edge)
pygeodesy/constants.py CHANGED
@@ -1,3 +1,4 @@
1
+
1
2
  # -*- coding: utf-8 -*-
2
3
 
3
4
  u'''Single-instance C{float} and C{int} constants across C{pygeodesy} modules and
@@ -11,11 +12,12 @@ from __future__ import division as _; del _ # PYCHOK semicolon
11
12
 
12
13
  from pygeodesy.basics import _copysign, isbool, iscomplex, isint, _0_0
13
14
  from pygeodesy.errors import _xError, _xError2, _xkwds_get1, _xkwds_item2
15
+ # from pygeodesy.fsums import _isFsum_2Tuple # _MODS
14
16
  # from pygeodesy.internals import _0_0 # from .basics
15
17
  from pygeodesy.interns import _INF_, _NAN_, _UNDER_
16
- # from pygeodesy.lazily import _ALL_LAZY # from .unitsBase
18
+ from pygeodesy.lazily import _ALL_MODS as _MODS, _ALL_LAZY
17
19
  # from pygeodesy.streprs import Fmt # from .unitsBase
18
- from pygeodesy.unitsBase import Float, Int, Radius, _ALL_LAZY, Fmt
20
+ from pygeodesy.unitsBase import Float, Int, Radius, Fmt
19
21
 
20
22
  from math import fabs, isinf, isnan, pi as _pi, sqrt
21
23
  try:
@@ -24,7 +26,7 @@ except ImportError: # Python 2-
24
26
  _inf, _nan = float(_INF_), float(_NAN_)
25
27
 
26
28
  __all__ = _ALL_LAZY.constants
27
- __version__ = '24.08.26'
29
+ __version__ = '24.09.28'
28
30
 
29
31
 
30
32
  def _copysign_0_0(y):
@@ -320,20 +322,30 @@ def isclose(a, b, rel_tol=1e-12, abs_tol=EPS0):
320
322
  return _isclose(a, b, rel_tol=rel_tol, abs_tol=abs_tol)
321
323
 
322
324
 
325
+ try:
326
+ from cmath import isfinite as _iscfinite
327
+ except ImportError: # Python 3.1-
328
+
329
+ def _iscfinite(x): # PYCHOK not self?
330
+ '''Mimick Python 3.2+ C{cmath.isfinite}.
331
+ '''
332
+ return _isfinite(x.real) and _isfinite(x.imag)
333
+
323
334
  try:
324
335
  from math import isfinite as _isfinite # in .ellipsoids, ...
325
336
  except ImportError: # Python 3.1-
326
337
 
327
- def _isfinite(x):
338
+ def _isfinite(x): # PYCHOK not self?
328
339
  '''Mimick Python 3.2+ C{math.isfinite}.
329
340
  '''
330
341
  return not (isinf(x) or isnan(x))
331
342
 
332
343
 
333
344
  def isfinite(obj):
334
- '''Check a finite C{scalar} or C{complex} value.
345
+ '''Check a finite C{scalar}, C{complex}, ... value.
335
346
 
336
- @arg obj: Value (C{scalar} or C{complex}).
347
+ @arg obj: Value (C{scalar}, C{complex}, an L{Fsum} or
348
+ L{Fsum2Tuple}).
337
349
 
338
350
  @return: C{False} if B{C{obj}} is C{INF}, C{NINF}
339
351
  or C{NAN}, C{True} otherwise.
@@ -344,7 +356,9 @@ def isfinite(obj):
344
356
  return (obj not in _INF_NAN_NINF) and _isfinite(obj)
345
357
  except Exception as x:
346
358
  if iscomplex(obj): # _isfinite(complex) thows TypeError
347
- return isfinite(obj.real) and isfinite(obj.imag)
359
+ return _iscfinite(obj)
360
+ if _MODS.fsums._isFsum_2Tuple(obj): # OverflowError
361
+ return obj.is_finite()
348
362
  raise _xError(x, Fmt.PAREN(isfinite.__name__, obj))
349
363
 
350
364
 
@@ -27,7 +27,7 @@ __all__ = (_ALL_DEPRECATED.deprecated_bases +
27
27
  _ALL_DEPRECATED.deprecated_classes +
28
28
  _ALL_DEPRECATED.deprecated_consterns +
29
29
  _ALL_DEPRECATED.deprecated_functions)
30
- __version__ = '24.07.02'
30
+ __version__ = '24.09.19'
31
31
 
32
32
  if _unLazy0:
33
33
  from pygeodesy.deprecated import bases, datum, nvector, rhumbBase, \
@@ -14,7 +14,7 @@ from pygeodesy.props import deprecated_function
14
14
  from pygeodesy.units import Number_, Scalar_
15
15
 
16
16
  __all__ = _ALL_DEPRECATED.deprecated_functions
17
- __version__ = '24.06.11'
17
+ __version__ = '24.09.19'
18
18
 
19
19
  _WGS84 = _UTM = object()
20
20
 
@@ -193,6 +193,14 @@ def fStrzs(floatstr): # PYCHOK no cover
193
193
  return _MODS.streprs.fstrzs(floatstr)
194
194
 
195
195
 
196
+ @deprecated_function
197
+ def Fsum2product(*xs, **kwds):
198
+ '''DEPRECATED on 2024.09.19, use L{Fsum}C{(*B{xs}, B{f2product}=True, ...)}.'''
199
+ F = _MODS.fsums.Fsum(**kwds)
200
+ _ = F.f2product(True)
201
+ return F._facc_args(xs, up=False) if xs else F
202
+
203
+
196
204
  @deprecated_function
197
205
  def hypot3(x, y, z): # PYCHOK no cover
198
206
  '''DEPRECATED, use function L{pygeodesy.hypot_}.'''
@@ -34,7 +34,7 @@ from pygeodesy.utily import m2km, unroll180, _unrollon, _unrollon3, \
34
34
  from math import degrees, radians
35
35
 
36
36
  __all__ = _ALL_LAZY.ellipsoidalBaseDI
37
- __version__ = '24.06.17'
37
+ __version__ = '24.09.26'
38
38
 
39
39
  _polar__ = 'polar?'
40
40
  _B2END = _1_5 # _intersect3 bearing to pseudo-end point factor
@@ -365,7 +365,7 @@ class LatLonEllipsoidalBaseDI(LatLonEllipsoidalBase):
365
365
  c3 = _d3(c, wrap=wrap) # XXX wrap=False?
366
366
 
367
367
  except (TypeError, ValueError) as x:
368
- raise _xError(x, Fmt.SQUARE(points=0), p1, this=self, tol=tol,
368
+ raise _xError(x, Fmt.INDEX(points=0), p1, this=self, tol=tol,
369
369
  closed=closed, height=height, wrap=wrap)
370
370
 
371
371
  # get the azimuthal equidistant projection, once
@@ -391,8 +391,8 @@ class LatLonEllipsoidalBaseDI(LatLonEllipsoidalBase):
391
391
  p1, i = p2, j
392
392
 
393
393
  except (TypeError, ValueError) as x:
394
- raise _xError(x, Fmt.SQUARE(points=i), p1,
395
- Fmt.SQUARE(points=j), p2, this=self, tol=tol,
394
+ raise _xError(x, Fmt.INDEX(points=i), p1,
395
+ Fmt.INDEX(points=j), p2, this=self, tol=tol,
396
396
  closed=closed, height=height, wrap=wrap)
397
397
 
398
398
  f, j = _fi_j2(f, len(Ps)) # like .vector3d.nearestOn6
pygeodesy/errors.py CHANGED
@@ -27,7 +27,7 @@ from pygeodesy.lazily import _ALL_LAZY, _ALL_MODS as _MODS, _getenv, _PYTHON_X_D
27
27
  from copy import copy as _copy
28
28
 
29
29
  __all__ = _ALL_LAZY.errors # _ALL_DOCS('_InvalidError', '_IsnotError') _under
30
- __version__ = '24.07.07'
30
+ __version__ = '24.09.26'
31
31
 
32
32
  _argument_ = 'argument'
33
33
  _box_ = 'box'
@@ -759,14 +759,16 @@ try:
759
759
  _ = {}.__or__ # {} | {} # Python 3.9+
760
760
 
761
761
  def _xkwds(kwds, **dflts):
762
- '''(INTERNAL) Update C{dflts} with specified C{kwds}.
762
+ '''(INTERNAL) Update C{dflts} with specified C{kwds},
763
+ i.e. C{copy(kwds).update(dflts)}.
763
764
  '''
764
- return (dflts | kwds) if kwds else dflts
765
+ return ((dflts | kwds) if kwds else dflts) if dflts else kwds
765
766
 
766
767
  except AttributeError:
767
768
 
768
769
  def _xkwds(kwds, **dflts): # PYCHOK expected
769
- '''(INTERNAL) Update C{dflts} with specified C{kwds}.
770
+ '''(INTERNAL) Update C{dflts} with specified C{kwds},
771
+ i.e. C{copy(kwds).update(dflts)}.
770
772
  '''
771
773
  d = dflts
772
774
  if kwds:
@@ -787,6 +789,20 @@ except AttributeError:
787
789
  # setattr(inst, NN(_UNDER_, n), v)
788
790
 
789
791
 
792
+ def _xkwds_from(orig, *args, **kwds):
793
+ '''(INTERNAL) Return the items from C{orig} with the keys
794
+ from C{kwds} and a value not in C{args} and C{kwds}.
795
+ '''
796
+ def _items(orig, args, items):
797
+ for n, m in items:
798
+ if n in orig: # n in (orig.keys() & kwds.keys())
799
+ t = orig[n]
800
+ if t is not m and t not in args:
801
+ yield n, t
802
+
803
+ return _items(orig, args, kwds.items())
804
+
805
+
790
806
  def _xkwds_get(kwds, **name_default):
791
807
  '''(INTERNAL) Get a C{kwds} value by C{name} or the
792
808
  C{default} if not present.
@@ -809,7 +825,8 @@ def _xkwds_get_(kwds, **names_defaults):
809
825
 
810
826
  def _xkwds_get1(kwds, **name_default):
811
827
  '''(INTERNAL) Get one C{kwds} value by C{name} or the
812
- C{default} if not present.
828
+ C{default} if not present. Raise an C{_UnexpectedError}
829
+ with any remaining keyword arguments.
813
830
  '''
814
831
  v, kwds = _xkwds_pop2(kwds, **name_default)
815
832
  if kwds:
@@ -842,6 +859,16 @@ def _xkwds_not(*args, **kwds):
842
859
  return dict((n, v) for n, v in kwds.items() if v not in args)
843
860
 
844
861
 
862
+ def _xkwds_pop(kwds, **name_default):
863
+ '''(INTERNAL) Pop an item by C{name} from C{kwds} and
864
+ return its value, otherwise return the C{default}.
865
+ '''
866
+ if isinstance(kwds, dict) and len(name_default) == 1:
867
+ for n, v in name_default.items():
868
+ return kwds.pop(n, v)
869
+ raise _xAssertionError(_xkwds_pop, kwds, **name_default)
870
+
871
+
845
872
  def _xkwds_pop2(kwds, **name_default):
846
873
  '''(INTERNAL) Pop a C{kwds} item by C{name} and return the value and
847
874
  reduced C{kwds} copy, otherwise the C{default} and original C{kwds}.
@@ -865,6 +892,14 @@ def _Xorder(_Coeffs, Error, **Xorder): # in .auxLat, .ktm, .rhumb.bases, .rhumb
865
892
  raise Error(X, m, txt_not_=_or(*t))
866
893
 
867
894
 
895
+ def _xsError(X, xs, i, x, *n, **kwds): # in .fmath, ._fstats, .fsums
896
+ '''(INTERNAL) Error for C{xs} or C{x}, item C{xs[i]}.
897
+ '''
898
+ return ((_xError(X, n[0], xs, **kwds) if n else
899
+ _xError(X, xs=xs, **kwds)) if x is xs else
900
+ _xError(X, _streprs.Fmt.INDEX(xs=i), x, **kwds))
901
+
902
+
868
903
  def _xStrError(*Refs, **name_value_Error): # in .gars, .geohash, .wgrs
869
904
  '''(INTERNAL) Create a C{TypeError} for C{Garef}, C{Geohash}, C{Wgrs}.
870
905
  '''