Skip to content
GitLab
Explore
Sign in
Primary navigation
Search or go to…
Project
pygwinc
Manage
Activity
Members
Labels
Plan
Issues
Issue boards
Milestones
Wiki
Requirements
Code
Merge requests
Repository
Branches
Commits
Tags
Repository graph
Compare revisions
Snippets
Locked files
Build
Pipelines
Jobs
Pipeline schedules
Test cases
Artifacts
Deploy
Releases
Container Registry
Model registry
Operate
Environments
Monitor
Incidents
Analyze
Value stream analytics
Contributor analytics
CI/CD analytics
Repository analytics
Code review analytics
Issue analytics
Insights
Model experiments
Help
Help
Support
GitLab documentation
Compare GitLab plans
Community forum
Contribute to GitLab
Provide feedback
Keyboard shortcuts
?
Snippets
Groups
Projects
Show more breadcrumbs
Jameson Rollins
pygwinc
Commits
cb833f46
Commit
cb833f46
authored
6 years ago
by
Jameson Graef Rollins
Browse files
Options
Downloads
Patches
Plain Diff
move Struct definition into it's own module
parent
bf1a28c2
No related branches found
Branches containing commit
No related tags found
Tags containing commit
No related merge requests found
Changes
4
Hide whitespace changes
Inline
Side-by-side
Showing
4 changed files
gwinc/gwinc_matlab.py
+1
-1
1 addition, 1 deletion
gwinc/gwinc_matlab.py
gwinc/ifo/__init__.py
+1
-217
1 addition, 217 deletions
gwinc/ifo/__init__.py
gwinc/struct.py
+245
-0
245 additions, 0 deletions
gwinc/struct.py
gwinc/util.py
+1
-0
1 addition, 0 deletions
gwinc/util.py
with
248 additions
and
218 deletions
gwinc/gwinc_matlab.py
+
1
−
1
View file @
cb833f46
...
...
@@ -6,7 +6,7 @@ import numpy as np
import
logging
from
.
ifo
import
Struct
,
dictlist2recarray
from
.
struct
import
Struct
from
.plot
import
plot_noise
# NOTE: gwinc needs to be imported before matlab for some very strange
...
...
This diff is collapsed.
Click to expand it.
gwinc/ifo/__init__.py
+
1
−
217
View file @
cb833f46
import
os
import
re
import
fnmatch
import
yaml
import
scipy
import
scipy.io
import
numpy
as
np
from
scipy.io.matlab.mio5_params
import
mat_struct
# HACK: fix loading number in scientific notation
#
# https://stackoverflow.com/questions/30458977/yaml-loads-5e-6-as-string-and-not-a-number
#
# An apparent bug in python-yaml prevents it from regognizing
# scientific notation as a float. The following is a modified version
# of the parser that recognize scientific notation appropriately.
#
loader
=
yaml
.
SafeLoader
loader
.
add_implicit_resolver
(
'
tag:yaml.org,2002:float
'
,
re
.
compile
(
'''
^(?:
[-+]?(?:[0-9][0-9_]*)
\\
.[0-9_]*(?:[eE][-+]?[0-9]+)?
|[-+]?(?:[0-9][0-9_]*)(?:[eE][-+]?[0-9]+)
|
\\
.[0-9_]+(?:[eE][-+][0-9]+)?
|[-+]?[0-9][0-9_]*(?::[0-5]?[0-9])+
\\
.[0-9_]*
|[-+]?
\\
.(?:inf|Inf|INF)
|
\\
.(?:nan|NaN|NAN))$
'''
,
re
.
X
),
list
(
'
-+0123456789.
'
))
def
dictlist2recarray
(
l
):
def
dtype
(
v
):
if
isinstance
(
v
,
int
):
return
float
else
:
return
type
(
v
)
# get dtypes from first element dict
dtypes
=
[(
k
,
dtype
(
v
))
for
k
,
v
in
l
[
0
].
items
()]
values
=
[
tuple
(
el
.
values
())
for
el
in
l
]
out
=
np
.
array
(
values
,
dtype
=
dtypes
)
return
out
.
view
(
np
.
recarray
)
class
Struct
(
object
):
"""
Matlab struct-like object
This is a simple implementation of a MATLAB struct-like object
that stores values as attributes of a simple class: and allows assigning to
attributes recursively, e.g.:
>>>
s
=
Struct
()
>>>
s
.
a
=
4
>>>
s
.
b
=
Struct
()
>>>
s
.
b
.
c
=
8
Various classmethods allow creating one of these objects from YAML
file, a nested dict, or a MATLAB struct object.
"""
# FIXME: This would be a way to allow setting nested struct
# attributes, e.g.:
#
# >>> s = Struct()
# >>> s.a.b.c = 4
#
# Usage of __getattr__ like this is dangerous and creates
# non-intuitive behavior (i.e. an empty struct is returned with
# accessing attributes that don't exist). Is there a way to
# accomplish this without that adverse side affect?
#
# def __getattr__(self, name):
# if name not in self.__dict__:
# self.__dict__[name] = Struct()
# return self.__dict__[name]
##########
def
__contains__
(
self
,
item
):
return
item
in
self
.
__dict__
def
to_dict
(
self
,
array
=
False
):
"""
Return nested dictionary representation of Struct.
If `array` is True any lists encountered will be turned into
numpy arrays, and lists of Structs will be turned into record
arrays. This is need to convert to structure arrays in
matlab.
"""
d
=
{}
for
k
,
v
in
self
.
__dict__
.
items
():
if
isinstance
(
v
,
Struct
):
d
[
k
]
=
v
.
to_dict
(
array
=
array
)
else
:
if
isinstance
(
v
,
list
):
try
:
# this should fail if the elements of v are
# not Struct
# FIXME: need cleaner way to do this
v
=
[
i
.
to_dict
(
array
=
array
)
for
i
in
v
]
if
array
:
v
=
dictlist2recarray
(
v
)
except
AttributeError
:
if
array
:
v
=
np
.
array
(
v
)
elif
isinstance
(
v
,
int
):
v
=
float
(
v
)
d
[
k
]
=
v
return
d
def
to_yaml
(
self
,
path
=
None
):
"""
Return YAML representation of Struct as nested dict.
Or write Struct to YAML file if file
'
path
'
argument
specified.
"""
y
=
yaml
.
dump
(
self
.
to_dict
(),
default_flow_style
=
False
)
if
path
:
with
open
(
path
,
'
w
'
)
as
f
:
f
.
write
(
y
)
else
:
return
y
# def __repr__(self):
# return self.to_yaml().strip('\n')
def
__str__
(
self
):
return
'
<GWINC Struct: {}>
'
.
format
(
list
(
self
.
__dict__
.
keys
()))
def
__iter__
(
self
):
return
iter
(
self
.
__dict__
)
def
walk
(
self
):
"""
Iterate over all leaves in the struct tree.
"""
for
k
,
v
in
self
.
__dict__
.
items
():
if
type
(
v
)
is
Struct
:
for
sk
,
sv
in
v
.
walk
():
yield
k
+
'
.
'
+
sk
,
sv
else
:
try
:
for
i
,
vv
in
enumerate
(
v
):
for
sk
,
sv
in
vv
.
walk
():
yield
'
{}[{}].{}
'
.
format
(
k
,
i
,
sk
),
sv
except
(
AttributeError
,
TypeError
):
yield
k
,
v
@classmethod
def
from_dict
(
cls
,
d
):
"""
Create Struct from nested dict.
"""
c
=
cls
()
for
k
,
v
in
d
.
items
():
if
type
(
v
)
==
dict
:
c
.
__dict__
[
k
]
=
Struct
.
from_dict
(
v
)
else
:
try
:
c
.
__dict__
[
k
]
=
list
(
map
(
Struct
.
from_dict
,
v
))
except
(
AttributeError
,
TypeError
):
c
.
__dict__
[
k
]
=
v
return
c
@classmethod
def
from_matstruct
(
cls
,
s
):
"""
Create Struct from scipy.io.matlab mat_struct object.
"""
c
=
cls
()
try
:
s
=
s
[
'
ifo
'
]
except
:
pass
for
k
,
v
in
s
.
__dict__
.
items
():
if
k
in
[
'
_fieldnames
'
]:
# skip these fields
pass
elif
type
(
v
)
is
mat_struct
:
c
.
__dict__
[
k
]
=
Struct
.
from_matstruct
(
v
)
else
:
# handle lists of Structs
try
:
c
.
__dict__
[
k
]
=
list
(
map
(
Struct
.
from_matstruct
,
v
))
except
:
c
.
__dict__
[
k
]
=
v
return
c
@classmethod
def
from_file
(
cls
,
path
):
"""
Load Struct from .yaml or GWINC .mat file.
File type will be determined by extension.
"""
(
root
,
ext
)
=
os
.
path
.
splitext
(
path
)
with
open
(
path
,
'
r
'
)
as
f
:
if
ext
in
[
'
.yaml
'
,
'
.yml
'
]:
d
=
yaml
.
load
(
f
,
Loader
=
loader
)
return
cls
.
from_dict
(
d
)
elif
ext
==
'
.mat
'
:
s
=
scipy
.
io
.
loadmat
(
f
,
squeeze_me
=
True
,
struct_as_record
=
False
)
return
cls
.
from_matstruct
(
s
)
else
:
raise
IOError
(
"
Unknown file type: {}
"
.
format
(
ext
))
from
..struct
import
Struct
def
available_ifos
():
"""
List available included IFO files
"""
...
...
@@ -234,13 +28,3 @@ def load_ifo(name_or_path):
name_or_path
+
'
.yaml
'
)
s
=
Struct
.
from_file
(
path
)
return
s
##################################################
if
__name__
==
'
__main__
'
:
import
sys
ifo
=
load_ifo
(
sys
.
argv
[
1
])
# print(ifo.to_yaml())
print
(
ifo
.
to_dict
())
This diff is collapsed.
Click to expand it.
gwinc/struct.py
0 → 100644
+
245
−
0
View file @
cb833f46
import
os
import
re
import
io
import
yaml
import
numpy
as
np
from
scipy.io
import
loadmat
from
scipy.io.matlab.mio5_params
import
mat_struct
# HACK: fix loading number in scientific notation
#
# https://stackoverflow.com/questions/30458977/yaml-loads-5e-6-as-string-and-not-a-number
#
# An apparent bug in python-yaml prevents it from regognizing
# scientific notation as a float. The following is a modified version
# of the parser that recognize scientific notation appropriately.
loader
=
yaml
.
SafeLoader
loader
.
add_implicit_resolver
(
'
tag:yaml.org,2002:float
'
,
re
.
compile
(
'''
^(?:
[-+]?(?:[0-9][0-9_]*)
\\
.[0-9_]*(?:[eE][-+]?[0-9]+)?
|[-+]?(?:[0-9][0-9_]*)(?:[eE][-+]?[0-9]+)
|
\\
.[0-9_]+(?:[eE][-+][0-9]+)?
|[-+]?[0-9][0-9_]*(?::[0-5]?[0-9])+
\\
.[0-9_]*
|[-+]?
\\
.(?:inf|Inf|INF)
|
\\
.(?:nan|NaN|NAN))$
'''
,
re
.
X
),
list
(
'
-+0123456789.
'
))
def
dictlist2recarray
(
l
):
def
dtype
(
v
):
if
isinstance
(
v
,
int
):
return
float
else
:
return
type
(
v
)
# get dtypes from first element dict
dtypes
=
[(
k
,
dtype
(
v
))
for
k
,
v
in
l
[
0
].
items
()]
values
=
[
tuple
(
el
.
values
())
for
el
in
l
]
out
=
np
.
array
(
values
,
dtype
=
dtypes
)
return
out
.
view
(
np
.
recarray
)
class
Struct
(
object
):
"""
Matlab struct-like object
This is a simple implementation of a MATLAB struct-like object
that stores values as attributes of a simple class: and allows
assigning to attributes recursively, e.g.:
>>>
s
=
Struct
()
>>>
s
.
a
=
4
>>>
s
.
b
=
Struct
()
>>>
s
.
b
.
c
=
8
Various classmethods allow creating one of these objects from YAML
file, a nested dict, or a MATLAB struct object.
"""
# FIXME: This would be a way to allow setting nested struct
# attributes, e.g.:
#
# >>> s = Struct()
# >>> s.a.b.c = 4
#
# Usage of __getattr__ like this is dangerous and creates
# non-intuitive behavior (i.e. an empty struct is returned when
# accessing attributes that don't exist). Is there a way to
# accomplish this without that adverse side affect?
#
# def __getattr__(self, name):
# if name not in self.__dict__:
# self.__dict__[name] = Struct()
# return self.__dict__[name]
##########
def
__contains__
(
self
,
item
):
return
item
in
self
.
__dict__
def
to_dict
(
self
,
array
=
False
):
"""
Return nested dictionary representation of Struct.
If `array` is True any lists encountered will be turned into
numpy arrays, and lists of Structs will be turned into record
arrays. This is needed to convert to structure arrays in
matlab.
"""
d
=
{}
for
k
,
v
in
self
.
__dict__
.
items
():
if
isinstance
(
v
,
type
(
self
)):
d
[
k
]
=
v
.
to_dict
(
array
=
array
)
else
:
if
isinstance
(
v
,
list
):
try
:
# this should fail if the elements of v are
# not Struct
# FIXME: need cleaner way to do this
v
=
[
i
.
to_dict
(
array
=
array
)
for
i
in
v
]
if
array
:
v
=
dictlist2recarray
(
v
)
except
AttributeError
:
if
array
:
v
=
np
.
array
(
v
)
elif
isinstance
(
v
,
int
):
v
=
float
(
v
)
d
[
k
]
=
v
return
d
def
to_yaml
(
self
,
path
=
None
):
"""
Return YAML representation of Struct.
Write YAML to `path` if specified.
"""
y
=
yaml
.
dump
(
self
.
to_dict
(),
default_flow_style
=
False
)
if
path
:
with
open
(
path
,
'
w
'
)
as
f
:
f
.
write
(
y
)
else
:
return
y
# def __repr__(self):
# return self.to_yaml().strip('\n')
def
__str__
(
self
):
return
'
<GWINC Struct: {}>
'
.
format
(
list
(
self
.
__dict__
.
keys
()))
def
__iter__
(
self
):
return
iter
(
self
.
__dict__
)
def
walk
(
self
):
"""
Iterate over all leaves in the struct tree.
"""
for
k
,
v
in
self
.
__dict__
.
items
():
if
isinstance
(
v
,
type
(
self
)):
for
sk
,
sv
in
v
.
walk
():
yield
k
+
'
.
'
+
sk
,
sv
else
:
try
:
for
i
,
vv
in
enumerate
(
v
):
for
sk
,
sv
in
vv
.
walk
():
yield
'
{}[{}].{}
'
.
format
(
k
,
i
,
sk
),
sv
except
(
AttributeError
,
TypeError
):
yield
k
,
v
def
to_txt
(
self
,
path
=
None
,
fmt
=
'
0.6e
'
,
delimiter
=
'
:
'
,
end
=
''
):
"""
Return text represenation of Struct, one element per line.
Struct keys use
'
.
'
to indicate hierarchy. The `fmt` keyword
controls the formatting of numeric values. MATLAB code can
generated with the following parameters:
>>>
ifo
.
to_txt
(
delimiter
=
'
=
'
,
end
=
'
;
'
)
Write text to `path` if specified.
"""
txt
=
io
.
StringIO
()
for
k
,
v
in
sorted
(
self
.
walk
()):
if
isinstance
(
v
,
(
int
,
long
,
float
,
complex
)):
base
=
fmt
elif
isinstance
(
v
,
np
.
ndarray
):
v
=
np
.
array2string
(
v
,
separator
=
''
,
max_line_width
=
np
.
Inf
,
formatter
=
{
'
all
'
:
lambda
x
:
"
{:0.6e}
"
.
format
(
x
)})
base
=
'
s
'
else
:
base
=
'
s
'
txt
.
write
(
u
'
{key}{delimiter}{value:{base}}{end}
\n
'
.
format
(
key
=
k
,
value
=
v
,
base
=
base
,
delimiter
=
delimiter
,
end
=
end
,
))
if
path
:
with
open
(
path
,
'
w
'
)
as
f
:
f
.
write
(
txt
.
getvalue
())
else
:
return
txt
.
getvalue
()
@classmethod
def
from_dict
(
cls
,
d
):
"""
Create Struct from nested dict.
"""
c
=
cls
()
for
k
,
v
in
d
.
items
():
if
type
(
v
)
==
dict
:
c
.
__dict__
[
k
]
=
Struct
.
from_dict
(
v
)
else
:
try
:
c
.
__dict__
[
k
]
=
list
(
map
(
Struct
.
from_dict
,
v
))
except
(
AttributeError
,
TypeError
):
c
.
__dict__
[
k
]
=
v
return
c
@classmethod
def
from_matstruct
(
cls
,
s
):
"""
Create Struct from scipy.io.matlab mat_struct object.
"""
c
=
cls
()
try
:
s
=
s
[
'
ifo
'
]
except
:
pass
for
k
,
v
in
s
.
__dict__
.
items
():
if
k
in
[
'
_fieldnames
'
]:
# skip these fields
pass
elif
type
(
v
)
is
mat_struct
:
c
.
__dict__
[
k
]
=
Struct
.
from_matstruct
(
v
)
else
:
# handle lists of Structs
try
:
c
.
__dict__
[
k
]
=
list
(
map
(
Struct
.
from_matstruct
,
v
))
except
:
c
.
__dict__
[
k
]
=
v
# try:
# c.__dict__[k] = float(v)
# except:
# c.__dict__[k] = v
return
c
@classmethod
def
from_file
(
cls
,
path
):
"""
Load Struct from .yaml or MATLAB .mat file.
File type will be determined by extension.
"""
(
root
,
ext
)
=
os
.
path
.
splitext
(
path
)
with
open
(
path
,
'
r
'
)
as
f
:
if
ext
in
[
'
.yaml
'
,
'
.yml
'
]:
d
=
yaml
.
load
(
f
,
Loader
=
loader
)
return
cls
.
from_dict
(
d
)
elif
ext
==
'
.mat
'
:
s
=
loadmat
(
f
,
squeeze_me
=
True
,
struct_as_record
=
False
)
return
cls
.
from_matstruct
(
s
)
else
:
raise
IOError
(
"
Unknown file type: {}
"
.
format
(
ext
))
This diff is collapsed.
Click to expand it.
gwinc/util.py
+
1
−
0
View file @
cb833f46
...
...
@@ -4,6 +4,7 @@ from scipy.io.matlab.mio5_params import mat_struct
from
scipy.io
import
loadmat
import
scipy.special
from
.struct
import
Struct
from
.noise.coatingthermal
import
getCoatDopt
...
...
This diff is collapsed.
Click to expand it.
Preview
0%
Loading
Try again
or
attach a new file
.
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Save comment
Cancel
Please
register
or
sign in
to comment