5cbd3f29e3
Fuzz / Run fuzz harnesses (${{ github.event_name == 'schedule' && 'nightly' || 'smoke' }}) (push) Has been cancelled
Create Releases / call-mac (push) Has been cancelled
Create Releases / call-linux (push) Has been cancelled
Create Releases / call-sdist (push) Has been cancelled
Create Releases / call-win (push) Has been cancelled
Create Releases / call-pyodide (push) Has been cancelled
Windows_No_Exception_CI / build (x64, 3.10) (push) Has been cancelled
Check URLs / build (push) Has been cancelled
Create Releases / Attest CI build artifacts (push) Has been cancelled
Create Releases / Check for Publish release build to pypi (push) Has been cancelled
Create Releases / Check for Publish preview build to test.pypi-weekly (push) Has been cancelled
Create Releases / Publish preview build to test.pypi-weekly (push) Has been cancelled
Create Releases / Check for Publish release build to test.pypi (rc-candidates) (push) Has been cancelled
Create Releases / Publish release build to test.pypi (push) Has been cancelled
Create Releases / Check for Publish preview build to pypi-weekly (push) Has been cancelled
Create Releases / Publish preview build to pypi-weekly (push) Has been cancelled
Create Releases / Publish release build to pypi (push) Has been cancelled
Create Releases / test source distribution (push) Has been cancelled
clang-tidy / clang-tidy (push) Has been cancelled
Lint / Validate SBOM (push) Has been cancelled
Lint / Enforce style (push) Has been cancelled
CI / Test windows-2022, 3.14, External, debug=0, unity_build=0, onnx_ml=1, autogen=0 (push) Has been cancelled
CI / Test windows-latest, 3.10, Internal, debug=0, unity_build=0, onnx_ml=1, autogen=0 (push) Has been cancelled
CI / Test windows-latest, 3.14, Internal, debug=0, unity_build=0, onnx_ml=1, autogen=0 (push) Has been cancelled
CI / Test windows-latest, 3.14t, Internal, debug=0, unity_build=0, onnx_ml=1, autogen=0 (push) Has been cancelled
CI / Test ubuntu-24.04, 3.14, Internal, debug=1, unity_build=0, onnx_ml=1, autogen=0 (push) Has been cancelled
CI / Test ubuntu-24.04, 3.14, External, debug=0, unity_build=1, onnx_ml=1, autogen=1 (push) Has been cancelled
CI / Test ubuntu-24.04, 3.14, External, debug=0, unity_build=0, onnx_ml=0, autogen=0 (push) Has been cancelled
CI / Test macos-latest, 3.10, Internal, debug=0, unity_build=0, onnx_ml=1, autogen=0 (push) Has been cancelled
CI / Test macos-latest, 3.14, Internal, debug=0, unity_build=0, onnx_ml=1, autogen=0 (push) Has been cancelled
CI / Test macos-latest, 3.14t, Internal, debug=0, unity_build=0, onnx_ml=1, autogen=0 (push) Has been cancelled
CI / Test ubuntu-24.04, 3.14, External, debug=0, unity_build=0, onnx_ml=1, autogen=0 (push) Has been cancelled
CI / Test ubuntu-24.04, 3.10, Internal, debug=0, unity_build=0, onnx_ml=1, autogen=0 (push) Has been cancelled
CI / Test ubuntu-24.04, 3.14, Internal, debug=0, unity_build=0, onnx_ml=1, autogen=0 (push) Has been cancelled
CI / Test ubuntu-24.04, 3.14t, Internal, debug=0, unity_build=0, onnx_ml=1, autogen=0 (push) Has been cancelled
Pixi CI / Install and lint (ubuntu-24.04-arm) (push) Has been cancelled
Pixi CI / Install and lint (windows-2022) (push) Has been cancelled
Pixi CI / Xcode generator build (push) Has been cancelled
Pixi CI / Install and test (macos-latest, default) (push) Has been cancelled
Pixi CI / Install and test (ubuntu-24.04-arm, default) (push) Has been cancelled
Pixi CI / Install and test (ubuntu-latest, default) (push) Has been cancelled
Pixi CI / Install and test (windows-2022, default) (push) Has been cancelled
Pixi CI / Install and test (macos-latest, oldies) (push) Has been cancelled
Pixi CI / Install and test (ubuntu-24.04-arm, oldies) (push) Has been cancelled
Pixi CI / Install and test (ubuntu-latest, oldies) (push) Has been cancelled
Pixi CI / Install and test (windows-2022, oldies) (push) Has been cancelled
CodeQL / Analyze (actions) (push) Has been cancelled
CodeQL / Analyze (cpp) (push) Has been cancelled
CodeQL / Analyze (python) (push) Has been cancelled
Copilot Setup Steps / copilot-setup-steps (push) Has been cancelled
Generate and publish ONNX docs / build (push) Has been cancelled
Generate and publish ONNX docs / deploy (push) Has been cancelled
Scorecard supply-chain security / Scorecard analysis (push) Has been cancelled
150 lines
4.8 KiB
Python
150 lines
4.8 KiB
Python
# Copyright (c) ONNX Project Contributors
|
|
|
|
# SPDX-License-Identifier: Apache-2.0
|
|
from __future__ import annotations
|
|
|
|
import locale as pylocale
|
|
import unicodedata
|
|
import warnings
|
|
|
|
import numpy as np
|
|
|
|
from onnx.reference.op_run import OpRun, RuntimeTypeError
|
|
|
|
|
|
class StringNormalizer(OpRun):
|
|
"""The operator is not really threadsafe as python cannot
|
|
play with two locales at the same time. stop words
|
|
should not be implemented here as the tokenization
|
|
usually happens after this steps.
|
|
"""
|
|
|
|
def _run(
|
|
self,
|
|
x,
|
|
case_change_action=None,
|
|
is_case_sensitive=None,
|
|
locale=None,
|
|
stopwords=None,
|
|
):
|
|
slocale = locale
|
|
if stopwords is None:
|
|
raw_stops = set()
|
|
stops = set()
|
|
else:
|
|
raw_stops = set(stopwords)
|
|
if case_change_action == "LOWER":
|
|
stops = {w.lower() for w in stopwords}
|
|
elif case_change_action == "UPPER":
|
|
stops = {w.upper() for w in stopwords}
|
|
else:
|
|
stops = set(stopwords)
|
|
res = np.empty(x.shape, dtype=x.dtype)
|
|
if len(x.shape) == 2:
|
|
for i in range(x.shape[1]):
|
|
self._run_column(
|
|
x[:, i],
|
|
res[:, i],
|
|
slocale=slocale,
|
|
stops=stops,
|
|
raw_stops=raw_stops,
|
|
is_case_sensitive=is_case_sensitive,
|
|
case_change_action=case_change_action,
|
|
)
|
|
elif len(x.shape) == 1:
|
|
self._run_column(
|
|
x,
|
|
res,
|
|
slocale=slocale,
|
|
stops=stops,
|
|
raw_stops=raw_stops,
|
|
is_case_sensitive=is_case_sensitive,
|
|
case_change_action=case_change_action,
|
|
)
|
|
else:
|
|
raise RuntimeTypeError("x must be a matrix or a vector.")
|
|
if len(res.shape) == 2 and res.shape[0] == 1:
|
|
res = np.array([[w for w in res.tolist()[0] if len(w) > 0]])
|
|
if res.shape[1] == 0:
|
|
res = np.array([[""]])
|
|
elif len(res.shape) == 1:
|
|
res = np.array([w for w in res.tolist() if len(w) > 0])
|
|
if len(res) == 0:
|
|
res = np.array([""])
|
|
return (res,)
|
|
|
|
@staticmethod
|
|
def _run_column(
|
|
cin,
|
|
cout,
|
|
slocale=None,
|
|
stops=None,
|
|
raw_stops=None,
|
|
is_case_sensitive=None,
|
|
case_change_action=None,
|
|
):
|
|
if pylocale.getlocale() != slocale:
|
|
try:
|
|
pylocale.setlocale(pylocale.LC_ALL, slocale)
|
|
except pylocale.Error as e:
|
|
warnings.warn(
|
|
f"Unknown local setting {slocale!r} (current: {pylocale.getlocale()!r}) - {e!r}.",
|
|
stacklevel=1,
|
|
)
|
|
cout[:] = cin[:]
|
|
|
|
for i in range(cin.shape[0]):
|
|
if isinstance(cout[i], float):
|
|
# nan
|
|
cout[i] = ""
|
|
else:
|
|
cout[i] = StringNormalizer.strip_accents_unicode(cout[i])
|
|
|
|
if is_case_sensitive and len(stops) > 0:
|
|
for i in range(cin.shape[0]):
|
|
cout[i] = StringNormalizer._remove_stopwords(cout[i], raw_stops)
|
|
|
|
if case_change_action == "LOWER":
|
|
for i in range(cin.shape[0]):
|
|
cout[i] = cout[i].lower()
|
|
elif case_change_action == "UPPER":
|
|
for i in range(cin.shape[0]):
|
|
cout[i] = cout[i].upper()
|
|
elif case_change_action != "NONE":
|
|
raise RuntimeError(
|
|
f"Unknown option for case_change_action: {case_change_action!r}."
|
|
)
|
|
|
|
if not is_case_sensitive and len(stops) > 0:
|
|
for i in range(cin.shape[0]):
|
|
cout[i] = StringNormalizer._remove_stopwords(cout[i], stops)
|
|
|
|
return cout
|
|
|
|
@staticmethod
|
|
def _remove_stopwords(text, stops):
|
|
spl = text.split(" ")
|
|
return " ".join(filter(lambda s: s not in stops, spl))
|
|
|
|
@staticmethod
|
|
def strip_accents_unicode(s):
|
|
"""Transforms accentuated unicode symbols into their simple counterpart.
|
|
Source: `sklearn/feature_extraction/text.py
|
|
<https://github.com/scikit-learn/scikit-learn/blob/main/sklearn/
|
|
feature_extraction/text.py#L115>`_.
|
|
|
|
Args:
|
|
s: string The string to strip
|
|
|
|
Returns:
|
|
the cleaned string
|
|
"""
|
|
try:
|
|
# If `s` is ASCII-compatible, then it does not contain any accented
|
|
# characters and we can avoid an expensive list comprehension
|
|
s.encode("ASCII", errors="strict")
|
|
return s # noqa: TRY300
|
|
except UnicodeEncodeError:
|
|
normalized = unicodedata.normalize("NFKD", s)
|
|
return "".join([c for c in normalized if not unicodedata.combining(c)])
|