pygeodesy 24.5.15__py2.py3-none-any.whl → 24.6.1__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.
- {PyGeodesy-24.5.15.dist-info → PyGeodesy-24.6.1.dist-info}/METADATA +6 -5
- PyGeodesy-24.6.1.dist-info/RECORD +116 -0
- pygeodesy/__init__.py +4 -4
- pygeodesy/albers.py +41 -41
- pygeodesy/auxilats/__init__.py +1 -1
- pygeodesy/auxilats/__main__.py +2 -2
- pygeodesy/auxilats/auxAngle.py +32 -31
- pygeodesy/auxilats/auxLat.py +80 -51
- pygeodesy/azimuthal.py +123 -124
- pygeodesy/basics.py +46 -10
- pygeodesy/booleans.py +13 -14
- pygeodesy/cartesianBase.py +25 -23
- pygeodesy/clipy.py +3 -3
- pygeodesy/constants.py +3 -3
- pygeodesy/css.py +50 -42
- pygeodesy/datums.py +42 -41
- pygeodesy/deprecated/functions.py +9 -3
- pygeodesy/dms.py +6 -6
- pygeodesy/ecef.py +41 -41
- pygeodesy/ellipsoidalBase.py +41 -41
- pygeodesy/ellipsoidalBaseDI.py +3 -4
- pygeodesy/ellipsoidalGeodSolve.py +2 -2
- pygeodesy/ellipsoidalKarney.py +3 -3
- pygeodesy/ellipsoidalNvector.py +11 -12
- pygeodesy/ellipsoids.py +45 -38
- pygeodesy/elliptic.py +3 -4
- pygeodesy/epsg.py +4 -3
- pygeodesy/errors.py +52 -20
- pygeodesy/etm.py +68 -65
- pygeodesy/fmath.py +44 -49
- pygeodesy/formy.py +129 -115
- pygeodesy/frechet.py +118 -103
- pygeodesy/fstats.py +21 -14
- pygeodesy/fsums.py +124 -80
- pygeodesy/gars.py +10 -9
- pygeodesy/geodesicw.py +19 -17
- pygeodesy/geodesicx/__init__.py +1 -1
- pygeodesy/geodesicx/__main__.py +2 -2
- pygeodesy/geodesicx/gx.py +39 -33
- pygeodesy/geodesicx/gxarea.py +12 -9
- pygeodesy/geodesicx/gxbases.py +3 -4
- pygeodesy/geodesicx/gxline.py +6 -8
- pygeodesy/geodsolve.py +29 -28
- pygeodesy/geohash.py +60 -57
- pygeodesy/geoids.py +34 -32
- pygeodesy/hausdorff.py +114 -101
- pygeodesy/heights.py +137 -130
- pygeodesy/internals.py +16 -11
- pygeodesy/interns.py +3 -6
- pygeodesy/iters.py +19 -17
- pygeodesy/karney.py +21 -17
- pygeodesy/ktm.py +25 -18
- pygeodesy/latlonBase.py +12 -11
- pygeodesy/lazily.py +6 -6
- pygeodesy/lcc.py +24 -25
- pygeodesy/ltp.py +143 -113
- pygeodesy/ltpTuples.py +207 -150
- pygeodesy/mgrs.py +26 -26
- pygeodesy/named.py +172 -90
- pygeodesy/namedTuples.py +33 -25
- pygeodesy/nvectorBase.py +8 -8
- pygeodesy/osgr.py +40 -48
- pygeodesy/points.py +18 -18
- pygeodesy/props.py +29 -16
- pygeodesy/rhumb/__init__.py +1 -1
- pygeodesy/rhumb/aux_.py +13 -15
- pygeodesy/rhumb/bases.py +12 -5
- pygeodesy/rhumb/ekx.py +24 -18
- pygeodesy/rhumb/solve.py +13 -10
- pygeodesy/simplify.py +16 -16
- pygeodesy/solveBase.py +18 -18
- pygeodesy/sphericalBase.py +17 -21
- pygeodesy/sphericalTrigonometry.py +21 -21
- pygeodesy/streprs.py +5 -5
- pygeodesy/trf.py +13 -11
- pygeodesy/triaxials.py +68 -64
- pygeodesy/units.py +35 -35
- pygeodesy/unitsBase.py +24 -11
- pygeodesy/ups.py +66 -70
- pygeodesy/utily.py +3 -3
- pygeodesy/utm.py +183 -187
- pygeodesy/utmups.py +38 -38
- pygeodesy/utmupsBase.py +104 -106
- pygeodesy/vector2d.py +6 -7
- pygeodesy/vector3d.py +16 -17
- pygeodesy/vector3dBase.py +4 -5
- pygeodesy/webmercator.py +43 -51
- PyGeodesy-24.5.15.dist-info/RECORD +0 -116
- {PyGeodesy-24.5.15.dist-info → PyGeodesy-24.6.1.dist-info}/WHEEL +0 -0
- {PyGeodesy-24.5.15.dist-info → PyGeodesy-24.6.1.dist-info}/top_level.txt +0 -0
pygeodesy/internals.py
CHANGED
|
@@ -3,11 +3,11 @@
|
|
|
3
3
|
u'''Mostly INTERNAL functions, except L{machine}, L{print_} and L{printf}.
|
|
4
4
|
'''
|
|
5
5
|
# from pygeodesy.basics import isiterablen # _MODS
|
|
6
|
-
# from pygeodesy.errors import _AttributeError, _error_init, _xError2 # _MODS
|
|
6
|
+
# from pygeodesy.errors import _AttributeError, _error_init, _UnexpectedError, _xError2 # _MODS
|
|
7
7
|
from pygeodesy.interns import NN, _COLON_, _DOT_, _ELLIPSIS_, _EQUALSPACED_, \
|
|
8
8
|
_immutable_, _NL_, _pygeodesy_, _PyPy__, _python_, \
|
|
9
|
-
_QUOTE1_, _QUOTE2_, _SPACE_, _UNDER_, _utf_8_
|
|
10
|
-
from pygeodesy.interns import _COMMA_,
|
|
9
|
+
_QUOTE1_, _QUOTE2_, _s_, _SPACE_, _sys, _UNDER_, _utf_8_
|
|
10
|
+
from pygeodesy.interns import _COMMA_, _Python_ # PYCHOK used!
|
|
11
11
|
# from pygeodesy.streprs import anstr, pairs, unstr # _MODS
|
|
12
12
|
|
|
13
13
|
import os as _os # in .lazily, ...
|
|
@@ -222,7 +222,7 @@ def _caller3(up): # in .lazily, .named
|
|
|
222
222
|
f.f_lineno) # line number
|
|
223
223
|
|
|
224
224
|
|
|
225
|
-
def
|
|
225
|
+
def _dunder_ismain(name):
|
|
226
226
|
'''(INTERNAL) Return C{name == '__main__'}.
|
|
227
227
|
'''
|
|
228
228
|
return name == '__main__'
|
|
@@ -353,6 +353,12 @@ def _passargs(*args):
|
|
|
353
353
|
return args
|
|
354
354
|
|
|
355
355
|
|
|
356
|
+
def _plural(noun, n):
|
|
357
|
+
'''(INTERNAL) Return C{noun}['s'] or C{NN}.
|
|
358
|
+
'''
|
|
359
|
+
return NN(noun, _s_) if n > 1 else (noun if n else NN)
|
|
360
|
+
|
|
361
|
+
|
|
356
362
|
def print_(*args, **nl_nt_prec_prefix__end_file_flush_sep_kwds): # PYCHOK no cover
|
|
357
363
|
'''Python 3+ C{print}-like formatting and printing.
|
|
358
364
|
|
|
@@ -497,7 +503,7 @@ def _usage(file_py, *args): # in .etm
|
|
|
497
503
|
m = _os_path.dirname(file_py).replace(_os.getcwd(), _ELLIPSIS_) \
|
|
498
504
|
.replace(_os.sep, _DOT_).strip()
|
|
499
505
|
b, x = _os_path.splitext(_os_path.basename(file_py))
|
|
500
|
-
if x == '.py' and not
|
|
506
|
+
if x == '.py' and not _dunder_ismain(b):
|
|
501
507
|
m = _DOT_(m or _pygeodesy_, b)
|
|
502
508
|
p = NN(_python_, _sys.version_info[0])
|
|
503
509
|
u = _COLON_(_dunder_nameof(_usage)[1:], NN)
|
|
@@ -536,17 +542,16 @@ def _version_ints(vs):
|
|
|
536
542
|
return tuple(_ints(vs))
|
|
537
543
|
|
|
538
544
|
|
|
539
|
-
__all__ = (machine
|
|
540
|
-
|
|
541
|
-
__version__ = '24.05.15'
|
|
545
|
+
__all__ = tuple(map(_dunder_nameof, (machine, print_, printf)))
|
|
546
|
+
__version__ = '24.05.25'
|
|
542
547
|
|
|
543
|
-
if
|
|
548
|
+
if _dunder_ismain(__name__): # PYCHOK no cover
|
|
544
549
|
|
|
545
550
|
from pygeodesy import _isfrozen, isLazy, version as vs
|
|
546
551
|
|
|
547
552
|
print_(_pygeodesy_, vs, *(_Pythonarchine() + _osversion2()
|
|
548
|
-
+ ['
|
|
549
|
-
'isLazy',
|
|
553
|
+
+ ['_isfrozen', _isfrozen,
|
|
554
|
+
'isLazy', isLazy]))
|
|
550
555
|
|
|
551
556
|
# **) MIT License
|
|
552
557
|
#
|
pygeodesy/interns.py
CHANGED
|
@@ -201,11 +201,10 @@ _distance_ = 'distance' # PYCHOK OK
|
|
|
201
201
|
_distant_ = _Prefix('distant') # PYCHOK OK
|
|
202
202
|
_doesn_t_exist_ = "doesn't exist" # PYCHOK OK
|
|
203
203
|
_DOT_ = Str_('.') # PYCHOK OK
|
|
204
|
-
|
|
204
|
+
_dunder_name_ = '__name__' # PYCHOK _DUNDER_(NN, _name_, NN)
|
|
205
205
|
_e_ = 'e' # PYCHOK OK
|
|
206
206
|
_E_ = 'E' # PYCHOK OK
|
|
207
207
|
_earth_ = 'earth' # PYCHOK OK
|
|
208
|
-
_east_ = 'east' # PYCHOK OK
|
|
209
208
|
_easting_ = 'easting' # PYCHOK OK
|
|
210
209
|
_ecef_ = 'ecef' # PYCHOK OK
|
|
211
210
|
_edge_ = 'edge' # PYCHOK OK
|
|
@@ -259,8 +258,8 @@ _isclockwise_ = 'isclockwise' # PYCHOK OK
|
|
|
259
258
|
_ispolar_ = 'ispolar' # PYCHOK OK
|
|
260
259
|
_j_ = 'j' # PYCHOK OK
|
|
261
260
|
_k0_ = 'k0' # PYCHOK OK
|
|
261
|
+
_keyword_ = 'keyword' # PYCHOK OK
|
|
262
262
|
_kind_ = 'kind' # PYCHOK OK
|
|
263
|
-
_knots_ = 'knots' # PYCHOK OK
|
|
264
263
|
_Krassovski1940_ = 'Krassovski1940' # PYCHOK OK
|
|
265
264
|
_Krassowsky1940_ = 'Krassowsky1940' # PYCHOK OK
|
|
266
265
|
_LANGLE_ = '<' # PYCHOK OK
|
|
@@ -317,7 +316,6 @@ _NLHASH_ = Str_(_NL_ + '# ') # PYCHOK OK
|
|
|
317
316
|
# _NLNL_ = _DNL_ # PYCHOK OK
|
|
318
317
|
_NN_ = 'NN' # PYCHOK OK
|
|
319
318
|
_no_ = _Prefix('no') # PYCHOK OK
|
|
320
|
-
_north_ = 'north' # PYCHOK OK
|
|
321
319
|
_northing_ = 'northing' # PYCHOK OK
|
|
322
320
|
_NorthPole_ = 'NorthPole' # PYCHOK OK
|
|
323
321
|
_not_ = _Prefix('not') # PYCHOK OK
|
|
@@ -394,7 +392,6 @@ _STAR_ = Str_('*') # PYCHOK OK
|
|
|
394
392
|
_start_ = 'start' # PYCHOK OK
|
|
395
393
|
_std_ = 'std' # PYCHOK OK
|
|
396
394
|
_stdev_ = 'stdev' # PYCHOK OK
|
|
397
|
-
_supported_ = 'supported' # PYCHOK OK
|
|
398
395
|
_tbd_ = 'tbd' # PYCHOK OK
|
|
399
396
|
_TILDE_ = '~' # PYCHOK OK
|
|
400
397
|
_to_ = 'to' # PYCHOK OK
|
|
@@ -450,7 +447,7 @@ _LR_PAIRS = {_LANGLE_: _RANGLE_,
|
|
|
450
447
|
|
|
451
448
|
__all__ = (_NN_, # NOT MISSING!
|
|
452
449
|
Str_.__name__) # classes
|
|
453
|
-
__version__ = '24.05.
|
|
450
|
+
__version__ = '24.05.21'
|
|
454
451
|
|
|
455
452
|
if __name__ == '__main__':
|
|
456
453
|
|
pygeodesy/iters.py
CHANGED
|
@@ -15,10 +15,10 @@ from pygeodesy.basics import islistuple, issubclassof, len2, \
|
|
|
15
15
|
from pygeodesy.errors import _IndexError, LenError, PointsError, \
|
|
16
16
|
_TypeError, _ValueError
|
|
17
17
|
# from pygeodesy.internals import _passarg # from .basics
|
|
18
|
-
from pygeodesy.interns import
|
|
19
|
-
|
|
18
|
+
from pygeodesy.interns import _0_, _composite_, _few_, _latlon_, \
|
|
19
|
+
_points_, _too_
|
|
20
20
|
from pygeodesy.lazily import _ALL_DOCS, _ALL_LAZY, _ALL_MODS as _MODS
|
|
21
|
-
from pygeodesy.named import
|
|
21
|
+
from pygeodesy.named import _Named, property_RO, Fmt
|
|
22
22
|
from pygeodesy.namedTuples import Point3Tuple, Points2Tuple
|
|
23
23
|
# from pygeodesy.props import property_RO # from .named
|
|
24
24
|
# from pygeodesy.streprs import Fmt # from .named
|
|
@@ -26,7 +26,7 @@ from pygeodesy.units import Int, Radius
|
|
|
26
26
|
from pygeodesy.utily import degrees2m, _Wrap, _1_0
|
|
27
27
|
|
|
28
28
|
__all__ = _ALL_LAZY.iters
|
|
29
|
-
__version__ = '
|
|
29
|
+
__version__ = '24.05.23'
|
|
30
30
|
|
|
31
31
|
_items_ = 'items'
|
|
32
32
|
_iterNumpy2len = 1 # adjustable for testing purposes
|
|
@@ -50,7 +50,7 @@ class _BaseIter(_Named):
|
|
|
50
50
|
_prev = _NOTHING
|
|
51
51
|
_wrap = False
|
|
52
52
|
|
|
53
|
-
def __init__(self, items, loop=0, dedup=False, Error=None, name
|
|
53
|
+
def __init__(self, items, loop=0, dedup=False, Error=None, **name):
|
|
54
54
|
'''New iterator over an iterable of B{C{items}}.
|
|
55
55
|
|
|
56
56
|
@arg items: Iterable (any C{type}, except composites).
|
|
@@ -58,7 +58,7 @@ class _BaseIter(_Named):
|
|
|
58
58
|
iterate index (non-negative C{int}).
|
|
59
59
|
@kwarg dedup: Skip duplicate items (C{bool}).
|
|
60
60
|
@kwarg Error: Error to raise (L{LenError}).
|
|
61
|
-
@kwarg name: Optional name (C{str}).
|
|
61
|
+
@kwarg name: Optional C{B{name}="items"} (C{str}).
|
|
62
62
|
|
|
63
63
|
@raise Error: Invalid B{C{items}} or sufficient number of B{C{items}}.
|
|
64
64
|
|
|
@@ -238,10 +238,11 @@ class _BaseIter(_Named):
|
|
|
238
238
|
class PointsIter(_BaseIter):
|
|
239
239
|
'''Iterator for C{points} with optional loop-back and copies.
|
|
240
240
|
'''
|
|
241
|
-
_base =
|
|
242
|
-
_Error =
|
|
241
|
+
_base = None
|
|
242
|
+
_Error = PointsError
|
|
243
|
+
_name = _points_
|
|
243
244
|
|
|
244
|
-
def __init__(self, points, loop=0, base=None, dedup=False, wrap=False, name
|
|
245
|
+
def __init__(self, points, loop=0, base=None, dedup=False, wrap=False, **name):
|
|
245
246
|
'''New L{PointsIter} iterator.
|
|
246
247
|
|
|
247
248
|
@arg points: C{Iterable} or C{list}, C{sequence}, C{set}, C{tuple},
|
|
@@ -252,13 +253,13 @@ class PointsIter(_BaseIter):
|
|
|
252
253
|
@kwarg dedup: Skip duplicate points (C{bool}).
|
|
253
254
|
@kwarg wrap: If C{True}, wrap or I{normalize} the enum-/iterated
|
|
254
255
|
B{C{points}} (C{bool}).
|
|
255
|
-
@kwarg name: Optional name (C{str}).
|
|
256
|
+
@kwarg name: Optional C{B{name}="points"} (C{str}).
|
|
256
257
|
|
|
257
258
|
@raise PointsError: Insufficient number of B{C{points}}.
|
|
258
259
|
|
|
259
260
|
@raise TypeError: Some B{C{points}} are not B{C{base}}.
|
|
260
261
|
'''
|
|
261
|
-
_BaseIter.__init__(self, points, loop=loop, dedup=dedup, name
|
|
262
|
+
_BaseIter.__init__(self, points, loop=loop, dedup=dedup, **name)
|
|
262
263
|
|
|
263
264
|
if base and not (isNumpy2(points) or isTuple2(points)):
|
|
264
265
|
self._base = base
|
|
@@ -310,12 +311,13 @@ class PointsIter(_BaseIter):
|
|
|
310
311
|
class LatLon2PsxyIter(PointsIter):
|
|
311
312
|
'''Iterate and convert for C{points} with optional loop-back and copies.
|
|
312
313
|
'''
|
|
313
|
-
_deg2m =
|
|
314
|
-
|
|
315
|
-
|
|
314
|
+
_deg2m = None
|
|
315
|
+
_name = _latlon_
|
|
316
|
+
_radius = None # keep degrees
|
|
317
|
+
_wrap = True
|
|
316
318
|
|
|
317
319
|
def __init__(self, points, loop=0, base=None, wrap=True, radius=None,
|
|
318
|
-
dedup=False, name
|
|
320
|
+
dedup=False, **name):
|
|
319
321
|
'''New L{LatLon2PsxyIter} iterator.
|
|
320
322
|
|
|
321
323
|
@note: The C{LatLon} latitude is considered the I{pseudo-y} and
|
|
@@ -331,13 +333,13 @@ class LatLon2PsxyIter(PointsIter):
|
|
|
331
333
|
@kwarg radius: Mean earth radius (C{meter}) for conversion from
|
|
332
334
|
C{degrees} to C{meter} (or C{radians} if C{B{radius}=1}).
|
|
333
335
|
@kwarg dedup: Skip duplicate points (C{bool}).
|
|
334
|
-
@kwarg name: Optional name (C{str}).
|
|
336
|
+
@kwarg name: Optional C{B{name}="latlon"} (C{str}).
|
|
335
337
|
|
|
336
338
|
@raise PointsError: Insufficient number of B{C{points}}.
|
|
337
339
|
|
|
338
340
|
@raise TypeError: Some B{C{points}} are not B{C{base}}-compatible.
|
|
339
341
|
'''
|
|
340
|
-
PointsIter.__init__(self, points, loop=loop, base=base, dedup=dedup, name
|
|
342
|
+
PointsIter.__init__(self, points, loop=loop, base=base, dedup=dedup, **name)
|
|
341
343
|
if not wrap:
|
|
342
344
|
self._wrap = False
|
|
343
345
|
if radius:
|
pygeodesy/karney.py
CHANGED
|
@@ -142,13 +142,14 @@ from __future__ import division as _; del _ # PYCHOK semicolon
|
|
|
142
142
|
from pygeodesy.basics import _copysign, int1s, isint, itemsorted, neg, unsigned0, \
|
|
143
143
|
_xgeographiclib, _zip, _version_info
|
|
144
144
|
from pygeodesy.constants import NAN, _isfinite as _math_isfinite, _0_0, \
|
|
145
|
-
_1_16th,
|
|
146
|
-
from pygeodesy.errors import GeodesicError, _ValueError, _xkwds,
|
|
145
|
+
_1_16th, _1_0, _2_0, _180_0, _N_180_0, _360_0
|
|
146
|
+
from pygeodesy.errors import GeodesicError, _ValueError, _xkwds, _xkwds_get1
|
|
147
147
|
from pygeodesy.fmath import cbrt, fremainder, norm2
|
|
148
148
|
# from pygeodesy.internals import _version_info # from .basics
|
|
149
|
-
from pygeodesy.interns import
|
|
150
|
-
|
|
151
|
-
|
|
149
|
+
from pygeodesy.interns import _2_, _a12_, _area_, _azi2_, _azi12_, _composite_, \
|
|
150
|
+
_lat1_, _lat2_, _lon1_, _lon2_, _m12_, _M12_, \
|
|
151
|
+
_M21_, _number_, _s12_, _S12_, _UNDER_, \
|
|
152
|
+
_BAR_, NN # PYCHOK used!
|
|
152
153
|
from pygeodesy.lazily import _ALL_DOCS, _ALL_LAZY, _ALL_MODS as _MODS, _getenv
|
|
153
154
|
from pygeodesy.named import ADict, _NamedBase, _NamedTuple, notImplemented, _Pass
|
|
154
155
|
from pygeodesy.props import deprecated_method, Property_RO
|
|
@@ -159,7 +160,7 @@ from pygeodesy.utily import atan2d, sincos2d, tand, _unrollon, fabs
|
|
|
159
160
|
# from math import fabs # from .utily
|
|
160
161
|
|
|
161
162
|
__all__ = _ALL_LAZY.karney
|
|
162
|
-
__version__ = '24.05.
|
|
163
|
+
__version__ = '24.05.31'
|
|
163
164
|
|
|
164
165
|
_K_2_0 = _getenv('PYGEODESY_GEOGRAPHICLIB', _2_) == _2_
|
|
165
166
|
_perimeter_ = 'perimeter'
|
|
@@ -168,10 +169,10 @@ _perimeter_ = 'perimeter'
|
|
|
168
169
|
class _GTuple(_NamedTuple): # in .testNamedTuples
|
|
169
170
|
'''(INTERNAL) Helper.
|
|
170
171
|
'''
|
|
171
|
-
def toGDict(self, **updates):
|
|
172
|
+
def toGDict(self, **updates): # NO name=NN
|
|
172
173
|
'''Convert this C{*Tuple} to a L{GDict}.
|
|
173
174
|
|
|
174
|
-
@kwarg updates: Optional items to apply (C{
|
|
175
|
+
@kwarg updates: Optional items to apply (C{name=value} pairs)
|
|
175
176
|
'''
|
|
176
177
|
r = GDict(_zip(self._Names_, self)) # strict=True
|
|
177
178
|
if updates:
|
|
@@ -359,12 +360,11 @@ class _CapsBase(_NamedBase): # in .auxilats, .geodesicx.gxbases
|
|
|
359
360
|
'''
|
|
360
361
|
self._debug = Caps._DEBUG_ALL if debug else 0
|
|
361
362
|
|
|
362
|
-
def _iter2tion(self, r,
|
|
363
|
+
def _iter2tion(self, r, iter=None, **unused):
|
|
363
364
|
'''(INTERNAL) Copy C{C{s}.iter} into C{B{r}._iteration}.
|
|
364
365
|
'''
|
|
365
|
-
|
|
366
|
-
|
|
367
|
-
self._iteration = r._iteration = i
|
|
366
|
+
if iter is not None:
|
|
367
|
+
self._iteration = r._iteration = iter
|
|
368
368
|
return r
|
|
369
369
|
|
|
370
370
|
|
|
@@ -468,7 +468,7 @@ class Inverse10Tuple(_GTuple):
|
|
|
468
468
|
|
|
469
469
|
@kwarg updates: Optional items to apply (C{nam=value} pairs)
|
|
470
470
|
'''
|
|
471
|
-
return _GTuple.toGDict(self, azi1=atan2d(self.salp1, self.calp1), # PYCHOK
|
|
471
|
+
return _GTuple.toGDict(self, azi1=atan2d(self.salp1, self.calp1), # PYCHOK namedTuple
|
|
472
472
|
azi2=atan2d(self.salp2, self.calp2), # PYCHOK namedTuple
|
|
473
473
|
**updates) # PYCHOK indent
|
|
474
474
|
|
|
@@ -750,7 +750,10 @@ def _polynomial(x, cs, i, j): # PYCHOK shared
|
|
|
750
750
|
# for c in cs[i+1:j]:
|
|
751
751
|
# s, t = _sum2_(s * x, t * x, c)
|
|
752
752
|
# return s # + t
|
|
753
|
-
s
|
|
753
|
+
s = cs[i]
|
|
754
|
+
i += 1
|
|
755
|
+
if x and i < j:
|
|
756
|
+
s, _ = _sum2_(s, _0_0, x=x, *cs[i:j])
|
|
754
757
|
return s # + t
|
|
755
758
|
|
|
756
759
|
|
|
@@ -843,11 +846,12 @@ def _sum2_(s, t, *vs, **x):
|
|
|
843
846
|
|
|
844
847
|
@note: NOT "error-free", see C{pygeodesy.test/testKarney.py}.
|
|
845
848
|
'''
|
|
846
|
-
x =
|
|
849
|
+
x = _xkwds_get1(x, x=_1_0)
|
|
850
|
+
p = x != _1_0
|
|
847
851
|
|
|
848
852
|
_s2, _u0 = _sum2, unsigned0
|
|
849
853
|
for v in vs:
|
|
850
|
-
if
|
|
854
|
+
if p:
|
|
851
855
|
s *= x
|
|
852
856
|
t *= x
|
|
853
857
|
if v:
|
|
@@ -857,7 +861,7 @@ def _sum2_(s, t, *vs, **x):
|
|
|
857
861
|
if s:
|
|
858
862
|
t += u # accumulate u into t
|
|
859
863
|
# elif t: # s == 0 implies t == 0
|
|
860
|
-
# raise _AssertionError(t=t,
|
|
864
|
+
# raise _AssertionError(t=t, txt_not_=_0_)
|
|
861
865
|
else:
|
|
862
866
|
s = _u0(u) # result is u, t = 0
|
|
863
867
|
else:
|
pygeodesy/ktm.py
CHANGED
|
@@ -48,10 +48,10 @@ from pygeodesy.constants import INF, _K0_UTM, PI, PI_2, _0_0s, _0_0, \
|
|
|
48
48
|
_1_0, _90_0, _copysignINF
|
|
49
49
|
from pygeodesy.datums import Datum, _spherical_datum, _WGS84, _EWGS84
|
|
50
50
|
# from pygeodesy.ellipsoids import _EWGS84 # from .datums
|
|
51
|
-
from pygeodesy.errors import _ValueError,
|
|
51
|
+
from pygeodesy.errors import _ValueError, _xkwds_pop2, _Xorder
|
|
52
52
|
from pygeodesy.fmath import hypot, hypot1
|
|
53
53
|
from pygeodesy.fsums import fsum1f_
|
|
54
|
-
from pygeodesy.interns import
|
|
54
|
+
from pygeodesy.interns import _COMMASPACE_, _singular_
|
|
55
55
|
from pygeodesy.karney import _atan2d, _diff182, _fix90, _norm180, \
|
|
56
56
|
_polynomial, _unsigned2
|
|
57
57
|
# from pygeodesy.lazily import _ALL_LAZY # from .named
|
|
@@ -67,7 +67,7 @@ from cmath import polar
|
|
|
67
67
|
from math import atan2, asinh, cos, cosh, degrees, fabs, sin, sinh, sqrt, tanh
|
|
68
68
|
|
|
69
69
|
__all__ = _ALL_LAZY.ktm
|
|
70
|
-
__version__ = '24.05.
|
|
70
|
+
__version__ = '24.05.24'
|
|
71
71
|
|
|
72
72
|
|
|
73
73
|
class KTMError(_ValueError):
|
|
@@ -115,24 +115,33 @@ class KTransverseMercator(_NamedBase):
|
|
|
115
115
|
_mTM = 6
|
|
116
116
|
_raiser = False # throw Error
|
|
117
117
|
|
|
118
|
-
def __init__(self, a_earth=_EWGS84, f=None, lon0=0, k0=_K0_UTM,
|
|
119
|
-
|
|
118
|
+
def __init__(self, a_earth=_EWGS84, f=None, lon0=0, k0=_K0_UTM,
|
|
119
|
+
raiser=False, **TMorder_name):
|
|
120
120
|
'''New L{KTransverseMercator}.
|
|
121
121
|
|
|
122
122
|
@kwarg a_earth: This rhumb's earth (L{Ellipsoid}, L{Ellipsoid2},
|
|
123
123
|
L{a_f2Tuple}, L{Datum}, 2-tuple (C{a, f})) or the
|
|
124
124
|
equatorial radius (C{scalar}, C{meter}).
|
|
125
|
-
@kwarg f: The ellipsoid's flattening (C{scalar}), iff B{C{a_earth}}
|
|
126
|
-
a C{scalar}, ignored otherwise.
|
|
125
|
+
@kwarg f: The ellipsoid's flattening (C{scalar}), iff B{C{a_earth}}
|
|
126
|
+
is a C{scalar}, ignored otherwise.
|
|
127
127
|
@kwarg lon0: The central meridian (C{degrees180}).
|
|
128
128
|
@kwarg k0: Central scale factor (C{scalar}).
|
|
129
|
-
@kwarg name: Optional name (C{str}).
|
|
130
129
|
@kwarg raiser: If C{True}, throw a L{KTMError} for C{forward}
|
|
131
130
|
singularities (C{bool}).
|
|
132
|
-
@kwarg
|
|
131
|
+
@kwarg TMorder_name: Optional C{B{name}=NN} (C{str}) and optional
|
|
132
|
+
keyword argument C{B{TMorder}=6} for the order of
|
|
133
|
+
this L{KTransverseMercator}, see property C{TMorder}.
|
|
133
134
|
|
|
134
135
|
@raise KTMError: Invalid B{C{a_earth}}, B{C{f}} or B{C{TMorder}}.
|
|
135
136
|
'''
|
|
137
|
+
if TMorder_name:
|
|
138
|
+
M = self._mTM
|
|
139
|
+
m, name = _xkwds_pop2(TMorder_name, TMorder=M)
|
|
140
|
+
if m != M:
|
|
141
|
+
self.TMorder = m
|
|
142
|
+
if name:
|
|
143
|
+
self.name = name
|
|
144
|
+
|
|
136
145
|
if f is not None:
|
|
137
146
|
self.ellipsoid = a_earth, f
|
|
138
147
|
elif a_earth in (_EWGS84, _WGS84, None):
|
|
@@ -141,14 +150,11 @@ class KTransverseMercator(_NamedBase):
|
|
|
141
150
|
self.datum = a_earth
|
|
142
151
|
else:
|
|
143
152
|
self.ellipsoid = a_earth
|
|
153
|
+
|
|
144
154
|
self.lon0 = lon0
|
|
145
155
|
self.k0 = k0
|
|
146
|
-
if name: # PYCHOK no cover
|
|
147
|
-
self.name = name
|
|
148
156
|
if raiser:
|
|
149
157
|
self.raiser = True
|
|
150
|
-
if TMorder:
|
|
151
|
-
self.TMorder = _xkwds_get(TMorder, TMorder=self._mTM)
|
|
152
158
|
|
|
153
159
|
@Property_RO
|
|
154
160
|
def _Alp(self):
|
|
@@ -215,13 +221,13 @@ class KTransverseMercator(_NamedBase):
|
|
|
215
221
|
|
|
216
222
|
f = flattening
|
|
217
223
|
|
|
218
|
-
def forward(self, lat, lon, lon0=None, name
|
|
224
|
+
def forward(self, lat, lon, lon0=None, **name):
|
|
219
225
|
'''Forward projection, from geographic to transverse Mercator.
|
|
220
226
|
|
|
221
227
|
@arg lat: Latitude of point (C{degrees90}).
|
|
222
228
|
@arg lon: Longitude of point (C{degrees180}).
|
|
223
229
|
@arg lon0: Central meridian of the projection (C{degrees180}).
|
|
224
|
-
@kwarg name: Optional name (C{str}).
|
|
230
|
+
@kwarg name: Optional C{B{name}=NN} (C{str}).
|
|
225
231
|
|
|
226
232
|
@return: L{Forward4Tuple}C{(easting, northing, gamma, scale)}
|
|
227
233
|
with C{easting} and C{northing} in C{meter}, unfalsed, the
|
|
@@ -272,7 +278,7 @@ class KTransverseMercator(_NamedBase):
|
|
|
272
278
|
y, g = neg_(y, g)
|
|
273
279
|
if _lon:
|
|
274
280
|
x, g = neg_(x, g)
|
|
275
|
-
return Forward4Tuple(x, y, _norm180(g), k, name=
|
|
281
|
+
return Forward4Tuple(x, y, _norm180(g), k, name=self._name__(name))
|
|
276
282
|
|
|
277
283
|
@property_doc_(''' the central scale factor (C{float}).''')
|
|
278
284
|
def k0(self):
|
|
@@ -347,12 +353,13 @@ class KTransverseMercator(_NamedBase):
|
|
|
347
353
|
self. lon0 = lon0
|
|
348
354
|
return t
|
|
349
355
|
|
|
350
|
-
def reverse(self, x, y, lon0=None, name
|
|
356
|
+
def reverse(self, x, y, lon0=None, **name):
|
|
351
357
|
'''Reverse projection, from transverse Mercator to geographic.
|
|
352
358
|
|
|
353
359
|
@arg x: Easting of point (C{meter}).
|
|
354
360
|
@arg y: Northing of point (C{meter}).
|
|
355
361
|
@arg lon0: Central meridian of the projection (C{degrees180}).
|
|
362
|
+
@kwarg name: Optional C{B{name}=NN} (C{str}).
|
|
356
363
|
|
|
357
364
|
@return: L{Reverse4Tuple}C{(lat, lon, gamma, scale)} with
|
|
358
365
|
C{lat}- and C{lon}gitude in C{degrees}, I{unfalsed}.
|
|
@@ -394,7 +401,7 @@ class KTransverseMercator(_NamedBase):
|
|
|
394
401
|
lat += self._lat0
|
|
395
402
|
lon += self._lon0 if lon0 is None else _norm180(lon0)
|
|
396
403
|
return Reverse4Tuple(lat, _norm180(lon), _norm180(g), k,
|
|
397
|
-
name=
|
|
404
|
+
name=self._name__(name))
|
|
398
405
|
|
|
399
406
|
@Property
|
|
400
407
|
def TMorder(self):
|
pygeodesy/latlonBase.py
CHANGED
|
@@ -53,7 +53,7 @@ from contextlib import contextmanager
|
|
|
53
53
|
from math import asin, cos, degrees, fabs, radians
|
|
54
54
|
|
|
55
55
|
__all__ = _ALL_LAZY.latlonBase
|
|
56
|
-
__version__ = '24.
|
|
56
|
+
__version__ = '24.05.18'
|
|
57
57
|
|
|
58
58
|
|
|
59
59
|
class LatLonBase(_NamedBase):
|
|
@@ -66,7 +66,7 @@ class LatLonBase(_NamedBase):
|
|
|
66
66
|
_lat = 0 # latitude (C{degrees})
|
|
67
67
|
_lon = 0 # longitude (C{degrees})
|
|
68
68
|
|
|
69
|
-
def __init__(self, latlonh, lon=None, height=0, wrap=False,
|
|
69
|
+
def __init__(self, latlonh, lon=None, height=0, wrap=False, datum=None, **name):
|
|
70
70
|
'''New C{LatLon}.
|
|
71
71
|
|
|
72
72
|
@arg latlonh: Latitude (C{degrees} or DMS C{str} with N or S suffix) or
|
|
@@ -77,9 +77,9 @@ class LatLonBase(_NamedBase):
|
|
|
77
77
|
(C{meter}, conventionally).
|
|
78
78
|
@kwarg wrap: If C{True}, wrap or I{normalize} B{C{lat}} and B{C{lon}}
|
|
79
79
|
(C{bool}).
|
|
80
|
-
@kwarg name: Optional name (C{str}).
|
|
81
80
|
@kwarg datum: Optional datum (L{Datum}, L{Ellipsoid}, L{Ellipsoid2},
|
|
82
81
|
L{a_f2Tuple} or I{scalar} radius) or C{None}.
|
|
82
|
+
@kwarg name: Optional C{B{name}=NN} (C{str}).
|
|
83
83
|
|
|
84
84
|
@return: New instance (C{LatLon}).
|
|
85
85
|
|
|
@@ -1418,13 +1418,14 @@ class LatLonBase(_NamedBase):
|
|
|
1418
1418
|
for p in (p, c):
|
|
1419
1419
|
e = _xattr(p, Ecef=None)
|
|
1420
1420
|
if e not in (None, E): # PYCHOK no cover
|
|
1421
|
-
n =
|
|
1422
|
-
|
|
1421
|
+
n, _ = _xkwds_item2(name_point)
|
|
1422
|
+
n = Fmt.INDEX(n, i)
|
|
1423
|
+
raise _ValueError(n, e, txt=_incompatible(E.__name__)) # txt__
|
|
1423
1424
|
return c
|
|
1424
1425
|
|
|
1425
|
-
def toDatum(self, datum2, height=None, name
|
|
1426
|
+
def toDatum(self, datum2, height=None, **name):
|
|
1426
1427
|
'''I{Must be overloaded}.'''
|
|
1427
|
-
self._notOverloaded(datum2, height=height, name
|
|
1428
|
+
self._notOverloaded(datum2, height=height, **name)
|
|
1428
1429
|
|
|
1429
1430
|
def toEcef(self, height=None, M=False):
|
|
1430
1431
|
'''Convert this point to I{geocentric} coordinates, also known as
|
|
@@ -1476,16 +1477,16 @@ class LatLonBase(_NamedBase):
|
|
|
1476
1477
|
return self._Ltp if Ecef in (None, self.Ecef) else self._ltp.Ltp(
|
|
1477
1478
|
self, ecef=Ecef(self.datum), name=self.name)
|
|
1478
1479
|
|
|
1479
|
-
def toNormal(self, deep=False, name
|
|
1480
|
+
def toNormal(self, deep=False, **name):
|
|
1480
1481
|
'''Get this point I{normalized} to C{abs(lat) <= 90}
|
|
1481
1482
|
and C{abs(lon) <= 180}.
|
|
1482
1483
|
|
|
1483
1484
|
@kwarg deep: If C{True} make a deep, otherwise a
|
|
1484
1485
|
shallow copy (C{bool}).
|
|
1485
|
-
@kwarg name: Optional name
|
|
1486
|
+
@kwarg name: Optional C{B{name}=NN} (C{str}).
|
|
1486
1487
|
|
|
1487
|
-
@return: A copy of this point, I{normalized}
|
|
1488
|
-
optionally renamed
|
|
1488
|
+
@return: A copy of this point, I{normalized} (C{LatLon}),
|
|
1489
|
+
optionally renamed.
|
|
1489
1490
|
|
|
1490
1491
|
@see: Property L{isnormal}, method L{normal} and function
|
|
1491
1492
|
L{pygeodesy.normal}.
|
pygeodesy/lazily.py
CHANGED
|
@@ -30,7 +30,7 @@ and line number.
|
|
|
30
30
|
from pygeodesy import internals as _internals, interns as _interns, \
|
|
31
31
|
_isfrozen # DON'T _lazy_import2
|
|
32
32
|
# from pygeodesy.errors import _error_init # _ALL_MODS
|
|
33
|
-
from pygeodesy.internals import _caller3, _dunder_nameof,
|
|
33
|
+
from pygeodesy.internals import _caller3, _dunder_nameof, _dunder_ismain, \
|
|
34
34
|
_headof, _osversion2, printf, _Pythonarchine, \
|
|
35
35
|
_tailof
|
|
36
36
|
from pygeodesy.interns import NN, _areaOf_, _attribute_, _by_, _COLONSPACE_, \
|
|
@@ -269,7 +269,7 @@ _ALL_LAZY = _NamedEnum_RO(_name='_ALL_LAZY',
|
|
|
269
269
|
'antipode', 'antipode_', 'bearing', 'bearing_',
|
|
270
270
|
'compassAngle', 'cosineForsytheAndoyerLambert', 'cosineForsytheAndoyerLambert_',
|
|
271
271
|
'cosineAndoyerLambert', 'cosineAndoyerLambert_', 'cosineLaw', 'cosineLaw_',
|
|
272
|
-
'equirectangular', '
|
|
272
|
+
'equirectangular', 'equirectangular4', 'euclidean', 'euclidean_',
|
|
273
273
|
'excessAbc_', 'excessCagnoli_', 'excessGirard_', 'excessLHuilier_',
|
|
274
274
|
'excessKarney', 'excessKarney_', 'excessQuad', 'excessQuad_',
|
|
275
275
|
'flatLocal', 'flatLocal_', 'flatPolar', 'flatPolar_',
|
|
@@ -421,7 +421,7 @@ _ALL_DEPRECATED = _NamedEnum_RO(_name='_ALL_DEPRECATED',
|
|
|
421
421
|
'R_M', 'R_MA', 'R_MB', 'R_KM', 'R_NM', 'R_SM', 'R_FM', 'R_VM'),
|
|
422
422
|
deprecated_functions=_i('anStr', 'areaof', 'atand', 'bounds', # most of the DEPRECATED functions, except ...
|
|
423
423
|
'clipCS3', 'clipDMS', 'clipStr', 'collins', 'copysign', # ... ellipsoidal, spherical flavors
|
|
424
|
-
'decodeEPSG2', 'encodeEPSG', 'enStr2', 'equirectangular3',
|
|
424
|
+
'decodeEPSG2', 'encodeEPSG', 'enStr2', 'equirectangular_', 'equirectangular3',
|
|
425
425
|
'excessAbc', 'excessGirard', 'excessLHuilier',
|
|
426
426
|
'false2f', 'falsed2f', 'float0', 'fStr', 'fStrzs', 'hypot3',
|
|
427
427
|
'inStr', 'isenclosedby', 'istuplist',
|
|
@@ -771,7 +771,7 @@ def _lazy_init2(pack):
|
|
|
771
771
|
_unLazy0 = _unlazy or not isLazy # pre-3.7 or w/o lazy import
|
|
772
772
|
|
|
773
773
|
if isLazy < 1: # not enabled
|
|
774
|
-
raise LazyImportError(_PYGEODESY_LAZY_IMPORT_, repr(z),
|
|
774
|
+
raise LazyImportError(_PYGEODESY_LAZY_IMPORT_, repr(z), txt_not_=_enabled_)
|
|
775
775
|
if _getenv('PYTHONVERBOSE', None): # PYCHOK no cover
|
|
776
776
|
isLazy += 1
|
|
777
777
|
|
|
@@ -805,7 +805,7 @@ def _lazy_module(name): # overwritten by _lazy_import2
|
|
|
805
805
|
# update the package's C{__dict__} accordingly.
|
|
806
806
|
# '''
|
|
807
807
|
# sm = dict()
|
|
808
|
-
# if force and not
|
|
808
|
+
# if force and not _dunder_ismain(_dunder_name_):
|
|
809
809
|
# nm = _tailof(_dunder_name_)
|
|
810
810
|
# _a = _ALL_MODS.getattr
|
|
811
811
|
# _m = _ALL_MODS.getmodule
|
|
@@ -827,7 +827,7 @@ def _lazy_module(name): # overwritten by _lazy_import2
|
|
|
827
827
|
|
|
828
828
|
# del _i, _i0
|
|
829
829
|
|
|
830
|
-
if
|
|
830
|
+
if _dunder_ismain(__name__): # PYCHOK no cover
|
|
831
831
|
|
|
832
832
|
from timeit import timeit
|
|
833
833
|
|