mrio-toolbox 1.1.1__py3-none-any.whl → 1.1.3__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.

Potentially problematic release.


This version of mrio-toolbox might be problematic. Click here for more details.

Files changed (61) hide show
  1. {mrio_toolbox-1.1.1.dist-info → mrio_toolbox-1.1.3.dist-info}/METADATA +2 -2
  2. mrio_toolbox-1.1.3.dist-info/RECORD +5 -0
  3. mrio_toolbox-1.1.3.dist-info/top_level.txt +1 -0
  4. mrio_toolbox/__init__.py +0 -21
  5. mrio_toolbox/_parts/_Axe.py +0 -539
  6. mrio_toolbox/_parts/_Part.py +0 -1698
  7. mrio_toolbox/_parts/__init__.py +0 -7
  8. mrio_toolbox/_parts/part_operations.py +0 -57
  9. mrio_toolbox/extractors/__init__.py +0 -20
  10. mrio_toolbox/extractors/downloaders.py +0 -36
  11. mrio_toolbox/extractors/emerging/__init__.py +0 -3
  12. mrio_toolbox/extractors/emerging/emerging_extractor.py +0 -117
  13. mrio_toolbox/extractors/eora/__init__.py +0 -3
  14. mrio_toolbox/extractors/eora/eora_extractor.py +0 -132
  15. mrio_toolbox/extractors/exiobase/__init__.py +0 -3
  16. mrio_toolbox/extractors/exiobase/exiobase_extractor.py +0 -270
  17. mrio_toolbox/extractors/extractors.py +0 -79
  18. mrio_toolbox/extractors/figaro/__init__.py +0 -3
  19. mrio_toolbox/extractors/figaro/figaro_downloader.py +0 -280
  20. mrio_toolbox/extractors/figaro/figaro_extractor.py +0 -187
  21. mrio_toolbox/extractors/gloria/__init__.py +0 -3
  22. mrio_toolbox/extractors/gloria/gloria_extractor.py +0 -202
  23. mrio_toolbox/extractors/gtap11/__init__.py +0 -7
  24. mrio_toolbox/extractors/gtap11/extraction/__init__.py +0 -3
  25. mrio_toolbox/extractors/gtap11/extraction/extractor.py +0 -129
  26. mrio_toolbox/extractors/gtap11/extraction/harpy_files/__init__.py +0 -6
  27. mrio_toolbox/extractors/gtap11/extraction/harpy_files/_header_sets.py +0 -279
  28. mrio_toolbox/extractors/gtap11/extraction/harpy_files/har_file.py +0 -262
  29. mrio_toolbox/extractors/gtap11/extraction/harpy_files/har_file_io.py +0 -974
  30. mrio_toolbox/extractors/gtap11/extraction/harpy_files/header_array.py +0 -300
  31. mrio_toolbox/extractors/gtap11/extraction/harpy_files/sl4.py +0 -229
  32. mrio_toolbox/extractors/gtap11/gtap_mrio/__init__.py +0 -6
  33. mrio_toolbox/extractors/gtap11/gtap_mrio/mrio_builder.py +0 -158
  34. mrio_toolbox/extractors/icio/__init__.py +0 -3
  35. mrio_toolbox/extractors/icio/icio_extractor.py +0 -121
  36. mrio_toolbox/extractors/wiod/__init__.py +0 -3
  37. mrio_toolbox/extractors/wiod/wiod_extractor.py +0 -143
  38. mrio_toolbox/mrio.py +0 -899
  39. mrio_toolbox/msm/__init__.py +0 -6
  40. mrio_toolbox/msm/multi_scale_mapping.py +0 -863
  41. mrio_toolbox/utils/__init__.py +0 -3
  42. mrio_toolbox/utils/converters/__init__.py +0 -5
  43. mrio_toolbox/utils/converters/pandas.py +0 -247
  44. mrio_toolbox/utils/converters/xarray.py +0 -130
  45. mrio_toolbox/utils/formatting/__init__.py +0 -0
  46. mrio_toolbox/utils/formatting/formatter.py +0 -528
  47. mrio_toolbox/utils/loaders/__init__.py +0 -7
  48. mrio_toolbox/utils/loaders/_loader.py +0 -312
  49. mrio_toolbox/utils/loaders/_loader_factory.py +0 -96
  50. mrio_toolbox/utils/loaders/_nc_loader.py +0 -184
  51. mrio_toolbox/utils/loaders/_np_loader.py +0 -112
  52. mrio_toolbox/utils/loaders/_pandas_loader.py +0 -128
  53. mrio_toolbox/utils/loaders/_parameter_loader.py +0 -386
  54. mrio_toolbox/utils/savers/__init__.py +0 -11
  55. mrio_toolbox/utils/savers/_path_checker.py +0 -37
  56. mrio_toolbox/utils/savers/_to_folder.py +0 -165
  57. mrio_toolbox/utils/savers/_to_nc.py +0 -60
  58. mrio_toolbox-1.1.1.dist-info/RECORD +0 -59
  59. mrio_toolbox-1.1.1.dist-info/top_level.txt +0 -1
  60. {mrio_toolbox-1.1.1.dist-info → mrio_toolbox-1.1.3.dist-info}/WHEEL +0 -0
  61. {mrio_toolbox-1.1.1.dist-info → mrio_toolbox-1.1.3.dist-info}/licenses/LICENSE +0 -0
@@ -1,3 +0,0 @@
1
- """
2
- This module provides utility functions and classes for loading, saving and converting MRIO tables.
3
- """
@@ -1,5 +0,0 @@
1
- """
2
- This module provides utility functions for converting Part objects to pandas DataFrames or xarray DataArrays.
3
- """
4
- from . import xarray
5
- from . import pandas
@@ -1,247 +0,0 @@
1
- """
2
- Routines for converting between Pandas DataFrames and Parts objects.
3
- """
4
-
5
- import pandas as pd
6
- import numpy as np
7
-
8
- def to_pandas(part):
9
- """Return the current Part object as a Pandas DataFrame
10
-
11
- Only applicable to Parts objects with 1 or 2 dimensions.
12
- """
13
- if part.ndim==2:
14
- return pd.DataFrame(part.data,
15
- index = part.axes[0].label(True),
16
- columns = part.axes[1].label(True))
17
- if part.ndim==1:
18
- return pd.DataFrame(part.data,index = part.axes[0].label(True))
19
- try:
20
- return to_pandas(part.squeeze())
21
- except:
22
- raise ValueError(f"Cannot convert a Part with {part.ndim} dimensions to DataFrame.")
23
-
24
-
25
- def make_part(df,name="from_df",
26
- label_detection=False,
27
- **kwargs):
28
- """Load a Part object from a Pandas DataFrame
29
-
30
- Parameters
31
- ----------
32
- df : DataFrame
33
- DataFrame to load
34
- label_detection : bool, optional
35
- Automatically detect labels, by default False
36
- If True, the DataFrame is scanned to detect labels (defined as non-numeric data)
37
- name : str, optional
38
- Name of the data variable to load, by default None.
39
- This can be left empty if there's a single variable in the DataFrame.
40
-
41
- Returns
42
- -------
43
- dict
44
- Data required to create the Part object
45
- """
46
- part_data = dict()
47
- if label_detection:
48
- df = autodecode_labels(df)
49
- part_data["data"] = df.to_numpy()
50
- ndim = df.ndim
51
-
52
- labels = []
53
- if ndim == 1:
54
- labels.append(convert_labels(df.index))
55
- else:
56
- labels.append(convert_labels(df.index))
57
- labels.append(convert_labels(df.columns))
58
- labels = disambiguate_labels(labels)
59
- part_data["labels"] = labels
60
- part_data["groupings"] = kwargs.pop("groupings",dict())
61
- part_data["metadata"] = kwargs.pop("metadata",dict())
62
- part_data["name"] = name
63
- for key in kwargs:
64
- part_data["metadata"][key] = kwargs[key]
65
- return part_data
66
-
67
- def autodecode_labels(df):
68
- """Automatically detect the labels from a DataFrame
69
-
70
- This is done by indentifying the indices and columns
71
- with non-numeric values.
72
- """
73
- def test_selection(df,row,col):
74
- """Test if a selection is numeric"""
75
- try:
76
- for col in df.iloc[row:,col]:
77
- pd.to_numeric(col)
78
- return True
79
- except ValueError:
80
- return False
81
-
82
- def try_reduce(df,row,col):
83
- """Try reducing the rectangle to the right or down"""
84
- if test_selection(df,row+1,col):
85
- return row+1,col
86
- elif test_selection(df,row,col+1):
87
- return row,col+1
88
- else:
89
- return row+1,col+1
90
-
91
- def try_expand(df,row,col):
92
- """Try expanding the rectangle to the left or up"""
93
- if not test_selection(df,row+1,col):
94
- return row+1,col
95
- elif not test_selection(df,row,col+1):
96
- return row,col+1
97
- else:
98
- return row, col
99
-
100
- def find_rectangle(df):
101
- """Find the largest rectangle with only numeric data"""
102
- row = 0
103
- col = 0
104
- while not test_selection(df,row,col):
105
- row,col = try_reduce(df,row,col)
106
- while not test_selection(df,row,col):
107
- #After the first while loop, we found only numeric data
108
- #We now expand to the top and the left
109
- #To make sure we didn't crop numerical data
110
- row,col = try_expand(df,row,col)
111
- return row,col
112
-
113
- #First, we find the largest rectangle with only numeric data
114
- row,col = find_rectangle(df)
115
-
116
- #And we remove potential nan axes and ensure types are ok
117
- data = pd.DataFrame(
118
- data=df.iloc[row:,col:],
119
- dtype=np.float64)
120
-
121
- #We count Nan axes as they offset label names
122
- row_offset = data.map(
123
- np.isnan
124
- ).all(1).sum()
125
- col_offset = data.map(
126
- np.isnan
127
- ).all(0).sum()
128
-
129
-
130
- data = data.dropna(axis=0,how="all")
131
- data = data.dropna(axis=1,how="all")
132
-
133
-
134
- #Then, we build the labels
135
- if col>0:
136
- col_names = df.iloc[:row,col-1+col_offset].to_list()
137
- if row > 1:
138
- labels = []
139
- sel = df.iloc[:row,col:].transpose()
140
- for column in sel.columns:
141
- labels.append(sel[column].dropna().unique())
142
- columns = pd.MultiIndex.from_product(
143
- labels,
144
- names = col_names)
145
- else:
146
- columns = pd.Index(
147
- df.iloc[
148
- :row,col:
149
- ].values.flatten(),
150
- name = col_names[0]
151
- )
152
-
153
- else:
154
- columns = None
155
- if row > 0:
156
- index_names = df.iloc[row-1+row_offset,:col].to_list()
157
- if col > 1:
158
- labels = []
159
- sel = df.iloc[row+row_offset:,:col]
160
- for column in sel.columns:
161
- labels.append(
162
- list(sel[column].dropna().unique())
163
- )
164
- index = pd.MultiIndex.from_product(
165
- labels,
166
- names = index_names)
167
- else:
168
- index = pd.Index(
169
- list(
170
- df.iloc[
171
- row:,:col
172
- ].values.flatten()
173
- ),
174
- name = index_names[0]
175
- )
176
- else:
177
- index = None
178
-
179
- #We build the formatted DataFrame
180
- output = pd.DataFrame(
181
- data = data.values,
182
- columns=columns,
183
- index = index
184
- )
185
-
186
- return output
187
-
188
- def convert_labels(index):
189
- """Convert a Pandas Index to a dictionary of labels
190
-
191
- Parameters
192
- ----------
193
- index : Index
194
- Pandas Index to convert
195
- """
196
- output = []
197
- if isinstance(index,pd.MultiIndex):
198
- for i in range(index.nlevels):
199
- name = index.names[i]
200
- if name is None:
201
- name = f"level_{i}"
202
- output.append(
203
- {name : list(index.levels[i].values)}
204
- )
205
- return output
206
- if index.name is None:
207
- return [{0:list(index.array)}]
208
- return [{index.name:list(index.array)}]
209
-
210
- def disambiguate_labels(labels):
211
- """Disambiguate the labels
212
-
213
- This allow solving labels ambiguity if the name was incorrectly loaded.
214
-
215
- Parameters
216
- ----------
217
- index : dict of str:list of str
218
- New index to disambiguate
219
- labels : list of str:list of str
220
- List of labels to disambiguate
221
- """
222
- ordered = []
223
- cleared = dict()
224
- flat_labels = [label_dim for label in labels for label_dim in label]
225
- values = []
226
- for label in labels:
227
- ordered.append([])
228
- for level in range(len(label)):
229
- name,value = list(
230
- label[level].keys()
231
- )[0],list(
232
- label[level].values()
233
- )[0]
234
- if name not in cleared.keys():
235
- if value in values:
236
- #We have a duplicate
237
- #We use the first occurrence as reference
238
- ref_name = cleared.keys()[list(cleared.values()).index(value)]
239
- ordered[-1].append(
240
- {ref_name:value}
241
- )
242
- cleared[name] = value
243
- ordered[-1].append(label[level])
244
- cleared[name] = value
245
- values.append(value)
246
-
247
- return ordered
@@ -1,130 +0,0 @@
1
- """
2
- Routines for converting between xarray DataArrays and Parts objects.
3
-
4
- """
5
- import pandas as pd
6
- import xarray as xr
7
- import numpy as np
8
-
9
- def to_DataArray(part):
10
- """
11
- Convert a Part object to an xarray DataArray
12
-
13
- Labels are directly passed to the DataArray as coords.
14
-
15
- Returns
16
- -------
17
- xr.DataArray
18
- Corresponding DataArray
19
- """
20
- developed = part.develop(squeeze=False) #Force non-squeeze to keep dimensions
21
- old_dims = part.get_dimensions()
22
- new_dims = developed.get_dimensions()
23
- if old_dims != new_dims:
24
- #We code the original dimensions in the metadata
25
- #Because netcdf files do not support multi-level attributes
26
- original_dims = [
27
- dim for axe in old_dims for dim in axe+["_sep_"]
28
- ]
29
- part.metadata["_original_dimensions"] = original_dims[:-1]
30
- #The last bit removes the last separator
31
- coords = list()
32
- for axe in developed.axes:
33
- coords.append(
34
- axe.label(True)
35
- )
36
- return xr.DataArray(
37
- data = developed.data,
38
- name = part.name,
39
- attrs = part.metadata,
40
- coords = coords
41
- )
42
-
43
- def to_DataSet(mrio):
44
- ds = xr.Dataset(
45
- attrs = mrio.metadata,
46
- coords = mrio.labels
47
- )
48
- for part in mrio.parts:
49
- ds[part] = mrio.parts[part].to_xarray()
50
- return ds
51
-
52
- def make_part(data,**kwargs):
53
- """
54
- Load a Part object from an xarray DataArray
55
-
56
- Parameters
57
- ----------
58
- data : DataArray
59
- Part object to load
60
- name : str, optional
61
- Name of the data variable to load, by default None.
62
- This can be left empty if there's a single variable in the DataArray.
63
-
64
- Returns
65
- -------
66
- dict
67
- Data required to create the Part object
68
- """
69
- part_data = dict()
70
-
71
- if isinstance(data,xr.Dataset):
72
- #Extract the data from the Dataset
73
- list_vars = list(data.data_vars)
74
- if len(list_vars) > 1:
75
- #In ambiguous cases, the name must be provided
76
- name = kwargs.get("name",None)
77
- else:
78
- name = list_vars[0]
79
- data = data[name]
80
- elif isinstance(data,xr.DataArray):
81
- name = data.name
82
-
83
- part_data["data"] = data.to_numpy()
84
-
85
- #Format the labels
86
- labels = []
87
- for key in data.dims:
88
- label = dict()
89
- index = data.indexes[key]
90
- label[index.name] = index.values.tolist()
91
- labels.append(label)
92
- part_data["name"] = name
93
- part_data["labels"] = labels
94
- part_data["metadata"] = kwargs.get("metadata",dict())
95
- for attr in data.attrs:
96
- #Add metadata
97
- part_data["metadata"][attr] = data.attrs[attr]
98
- part_data["groupings"] = kwargs.get("groupings",dict())
99
- return part_data
100
-
101
- def make_mrio(data,**kwargs):
102
- """
103
- Load an MRIO object from an xarray DataSet
104
-
105
- Parameters
106
- ----------
107
- data : DataArray
108
- Part object to load
109
-
110
- Returns
111
- -------
112
- dict
113
- Data required to create the Part object
114
- """
115
- #Extract the data from the xarray
116
- list_vars = list(data.data_vars)
117
- to_load = kwargs.get("parts",list_vars)
118
-
119
- mrio_data = dict()
120
-
121
- labels = dict()
122
- for coord in data.coords:
123
- labels[coord] = data[coord].values.tolist()
124
- mrio_data["labels"] = labels
125
- mrio_data["groupings"] = kwargs.get("groupings",dict())
126
- mrio_data["groupings"].update(data.attrs.get("groupings",dict()))
127
- mrio_data["metadata"] = data.attrs
128
- mrio_data["metadata"].update(kwargs.get("metadata",dict()))
129
- mrio_data["parts"] = dict()
130
- return {"data":mrio_data},to_load
File without changes