upgini 1.2.156.dev4__tar.gz → 1.2.156.dev5__tar.gz

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.
Files changed (83) hide show
  1. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/PKG-INFO +1 -1
  2. upgini-1.2.156.dev5/src/upgini/__about__.py +1 -0
  3. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/autofe/binary.py +113 -16
  4. upgini-1.2.156.dev4/src/upgini/__about__.py +0 -1
  5. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/.gitignore +0 -0
  6. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/LICENSE +0 -0
  7. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/README.md +0 -0
  8. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/pyproject.toml +0 -0
  9. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/__init__.py +0 -0
  10. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/ads.py +0 -0
  11. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/ads_management/__init__.py +0 -0
  12. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/ads_management/ads_manager.py +0 -0
  13. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/autofe/__init__.py +0 -0
  14. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/autofe/all_operators.py +0 -0
  15. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/autofe/date.py +0 -0
  16. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/autofe/feature.py +0 -0
  17. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/autofe/groupby.py +0 -0
  18. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/autofe/operator.py +0 -0
  19. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/autofe/timeseries/__init__.py +0 -0
  20. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/autofe/timeseries/base.py +0 -0
  21. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/autofe/timeseries/cross.py +0 -0
  22. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/autofe/timeseries/delta.py +0 -0
  23. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/autofe/timeseries/lag.py +0 -0
  24. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/autofe/timeseries/roll.py +0 -0
  25. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/autofe/timeseries/trend.py +0 -0
  26. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/autofe/timeseries/volatility.py +0 -0
  27. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/autofe/unary.py +0 -0
  28. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/autofe/utils.py +0 -0
  29. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/autofe/vector.py +0 -0
  30. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/data_source/__init__.py +0 -0
  31. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/data_source/data_source_publisher.py +0 -0
  32. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/dataset.py +0 -0
  33. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/errors.py +0 -0
  34. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/features_enricher.py +0 -0
  35. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/http.py +0 -0
  36. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/mdc/__init__.py +0 -0
  37. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/mdc/context.py +0 -0
  38. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/metadata.py +0 -0
  39. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/metrics.py +0 -0
  40. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/normalizer/__init__.py +0 -0
  41. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/normalizer/normalize_utils.py +0 -0
  42. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/resource_bundle/__init__.py +0 -0
  43. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/resource_bundle/exceptions.py +0 -0
  44. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/resource_bundle/strings.properties +0 -0
  45. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/resource_bundle/strings_widget.properties +0 -0
  46. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/sampler/__init__.py +0 -0
  47. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/sampler/base.py +0 -0
  48. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/sampler/random_under_sampler.py +0 -0
  49. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/sampler/utils.py +0 -0
  50. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/search_task.py +0 -0
  51. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/spinner.py +0 -0
  52. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/Roboto-Regular.ttf +0 -0
  53. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/__init__.py +0 -0
  54. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/base_search_key_detector.py +0 -0
  55. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/blocked_time_series.py +0 -0
  56. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/config.py +0 -0
  57. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/country_utils.py +0 -0
  58. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/custom_loss_utils.py +0 -0
  59. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/cv_utils.py +0 -0
  60. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/datetime_utils.py +0 -0
  61. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/deduplicate_utils.py +0 -0
  62. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/display_utils.py +0 -0
  63. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/email_utils.py +0 -0
  64. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/fallback_progress_bar.py +0 -0
  65. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/feature_info.py +0 -0
  66. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/features_validator.py +0 -0
  67. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/format.py +0 -0
  68. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/hash_utils.py +0 -0
  69. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/ip_utils.py +0 -0
  70. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/mstats.py +0 -0
  71. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/one_hot_encoder.py +0 -0
  72. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/phone_utils.py +0 -0
  73. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/postal_code_utils.py +0 -0
  74. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/progress_bar.py +0 -0
  75. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/psi.py +0 -0
  76. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/sample_utils.py +0 -0
  77. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/sklearn_ext.py +0 -0
  78. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/sort.py +0 -0
  79. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/target_utils.py +0 -0
  80. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/track_info.py +0 -0
  81. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/ts_utils.py +0 -0
  82. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/utils/warning_counter.py +0 -0
  83. {upgini-1.2.156.dev4 → upgini-1.2.156.dev5}/src/upgini/version_validator.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.3
2
2
  Name: upgini
3
- Version: 1.2.156.dev4
3
+ Version: 1.2.156.dev5
4
4
  Summary: Intelligent data search & enrichment for Machine Learning
5
5
  Project-URL: Bug Reports, https://github.com/upgini/upgini/issues
6
6
  Project-URL: Homepage, https://upgini.com/
@@ -0,0 +1 @@
1
+ __version__ = "1.2.156.dev5"
@@ -140,23 +140,120 @@ class Distance(PandasOperator):
140
140
  is_symmetrical: bool = True
141
141
  has_symmetry_importance: bool = True
142
142
 
143
+ def _to_float_vector(self, value) -> Optional[np.ndarray]:
144
+ if value is None or (isinstance(value, float) and np.isnan(value)):
145
+ return None
146
+ return np.atleast_1d(np.asarray(value, dtype=np.float64))
147
+
148
+ def _stack_vectors(self, arr: np.ndarray, indices: np.ndarray) -> Optional[np.ndarray]:
149
+ try:
150
+ stacked = np.vstack(arr[indices])
151
+ except (ValueError, TypeError):
152
+ return None
153
+ if stacked.ndim != 2 or stacked.shape[1] == 0:
154
+ return None
155
+ if stacked.dtype != np.float64:
156
+ stacked = stacked.astype(np.float64, copy=False)
157
+ return stacked
158
+
159
+ def _cosine_distance_stacked(self, left_mat: np.ndarray, right_mat: np.ndarray) -> np.ndarray:
160
+ if left_mat.shape != right_mat.shape:
161
+ raise ValueError("Left and right matrices must have the same shape")
162
+ dots = np.sum(left_mat * right_mat, axis=1)
163
+ denom = np.sqrt(np.sum(left_mat * left_mat, axis=1)) * np.sqrt(np.sum(right_mat * right_mat, axis=1))
164
+ results = np.full(len(left_mat), np.nan, dtype=np.float64)
165
+ valid = denom > 0
166
+ results[valid] = 1 - dots[valid] / denom[valid]
167
+ return results
168
+
169
+ def _try_fast_distance(
170
+ self, left_arr: np.ndarray, right_arr: np.ndarray, row_present: np.ndarray, n: int
171
+ ) -> Optional[np.ndarray]:
172
+ valid_idx = np.flatnonzero(row_present)
173
+ if len(valid_idx) == 0:
174
+ return None
175
+
176
+ left_mat = self._stack_vectors(left_arr, valid_idx)
177
+ right_mat = self._stack_vectors(right_arr, valid_idx)
178
+ if left_mat is None or right_mat is None:
179
+ return None
180
+
181
+ stacked_results = self._cosine_distance_stacked(left_mat, right_mat)
182
+ if row_present.all():
183
+ return stacked_results
184
+
185
+ results = np.full(n, np.nan, dtype=np.float64)
186
+ results[valid_idx] = stacked_results
187
+ return results
188
+
189
+ def _parse_vectors(self, left_arr: np.ndarray, right_arr: np.ndarray) -> tuple[list, list, np.ndarray]:
190
+ n = len(left_arr)
191
+ left_vecs: list[Optional[np.ndarray]] = [None] * n
192
+ right_vecs: list[Optional[np.ndarray]] = [None] * n
193
+ row_valid = np.zeros(n, dtype=bool)
194
+ for i, (left_value, right_value) in enumerate(zip(left_arr, right_arr)):
195
+ left_vec = self._to_float_vector(left_value)
196
+ right_vec = self._to_float_vector(right_value)
197
+ left_vecs[i] = left_vec
198
+ right_vecs[i] = right_vec
199
+ if left_vec is not None and right_vec is not None and left_vec.size > 0 and right_vec.size > 0:
200
+ row_valid[i] = True
201
+ return left_vecs, right_vecs, row_valid
202
+
203
+ def _masked_cosine_distance(
204
+ self, left_mat: np.ndarray, right_mat: np.ndarray, row_valid: np.ndarray
205
+ ) -> np.ndarray:
206
+ results = self._cosine_distance_stacked(left_mat, right_mat)
207
+ if len(results) == len(row_valid):
208
+ results[~row_valid] = np.nan
209
+ return results
210
+
211
+ def _calculate_rowwise(
212
+ self, results: np.ndarray, indices: np.ndarray, left_vecs: list, right_vecs: list
213
+ ) -> None:
214
+ for index in indices:
215
+ left_vec = left_vecs[index]
216
+ right_vec = right_vecs[index]
217
+ dot = np.sum(left_vec * right_vec)
218
+ denom = np.sqrt(np.sum(left_vec * left_vec)) * np.sqrt(np.sum(right_vec * right_vec))
219
+ if denom != 0:
220
+ results[index] = 1 - dot / denom
221
+
222
+ def _calculate_fallback_distance(
223
+ self, left_arr: np.ndarray, right_arr: np.ndarray, n: int, index: pd.Index
224
+ ) -> pd.Series:
225
+ results = np.full(n, np.nan, dtype=np.float64)
226
+ left_vecs, right_vecs, row_valid = self._parse_vectors(left_arr, right_arr)
227
+ if not row_valid.any():
228
+ return pd.Series(results, index=index, dtype=np.float64)
229
+
230
+ valid_idx = np.flatnonzero(row_valid)
231
+ dim = left_vecs[valid_idx[0]].size
232
+ if not all(left_vecs[i].size == dim and right_vecs[i].size == dim for i in valid_idx):
233
+ self._calculate_rowwise(results, valid_idx, left_vecs, right_vecs)
234
+ return pd.Series(results, index=index, dtype=np.float64)
235
+
236
+ left_mat = np.zeros((n, dim), dtype=np.float64)
237
+ right_mat = np.zeros((n, dim), dtype=np.float64)
238
+ left_mat[valid_idx] = np.stack([left_vecs[i] for i in valid_idx])
239
+ right_mat[valid_idx] = np.stack([right_vecs[i] for i in valid_idx])
240
+
241
+ return pd.Series(self._masked_cosine_distance(left_mat, right_mat, row_valid), index=index, dtype=np.float64)
242
+
143
243
  def calculate_binary(self, left: pd.Series, right: pd.Series) -> pd.Series:
144
- return pd.Series(
145
- 1 - self.__dot(left, right) / (self.__norm(left) * self.__norm(right)), index=left.index
146
- ).astype(np.float64)
147
-
148
- # row-wise dot product, handling None values
149
- def __dot(self, left: pd.Series, right: pd.Series) -> pd.Series:
150
- left = left.apply(lambda x: np.array(x).astype(np.float64))
151
- right = right.apply(lambda x: np.array(x).astype(np.float64))
152
- res = (left.dropna() * right.dropna()).apply(np.sum)
153
- res = res.reindex(left.index.union(right.index))
154
- return res
155
-
156
- # Calculate the norm of a vector, handling None values
157
- def __norm(self, vector: pd.Series) -> pd.Series:
158
- vector = vector.fillna(np.nan)
159
- return np.sqrt(self.__dot(vector, vector))
244
+ n = len(left)
245
+ if n == 0:
246
+ return pd.Series(np.full(n, np.nan), index=left.index, dtype=np.float64)
247
+
248
+ row_present = left.notna().to_numpy() & right.notna().to_numpy()
249
+ left_arr = left.to_numpy()
250
+ right_arr = right.to_numpy()
251
+
252
+ fast_results = self._try_fast_distance(left_arr, right_arr, row_present, n)
253
+ if fast_results is not None:
254
+ return pd.Series(fast_results, index=left.index, dtype=np.float64)
255
+
256
+ return self._calculate_fallback_distance(left_arr, right_arr, n, left.index)
160
257
 
161
258
 
162
259
  # Left for backward compatibility
@@ -1 +0,0 @@
1
- __version__ = "1.2.156.dev4"
File without changes
File without changes
File without changes