We are currently solving the following issue within our repository. Here is the issue text:
--- BEGIN ISSUE ---
[BUG] Irreproducible results with `MultiRocketMultivariate`
`random_state` does guarantee the same results for each run.

```python
rng = np.random.default_rng()

X = pd.DataFrame([
    pd.Series([
        pd.Series(rng.integers(0, 10, 100)).astype(float),
        pd.Series(rng.integers(0, 10, 100)).astype(float),
    ]),
    pd.Series([
        pd.Series(rng.integers(0, 10, 100)).astype(float),
        pd.Series(rng.integers(0, 10, 100)).astype(float),
    ]),
])

MultiRocketMultivariate(random_state=42, num_kernels=84).fit_transform(X) - MultiRocketMultivariate(random_state=42, num_kernels=84).fit_transform(X)
```

The output should always be a `DataFrame` of zeros, but this is not the case.

<details>

<!--
Please run the following code snippet and paste the output here:

from sktime import show_versions; show_versions()
-->

System:
    python: 3.9.6 (default, Aug 11 2023, 19:44:49)  [Clang 15.0.0 (clang-1500.0.40.1)]
executable: /Users/temp/sktime/venv/bin/python
   machine: macOS-14.1.2-arm64-arm-64bit

Python dependencies:
          pip: 23.3.1
       sktime: 0.25.0
      sklearn: 1.3.2
       skbase: 0.4.6
        numpy: 1.26.1
        scipy: 1.11.3
       pandas: 2.1.4
   matplotlib: 3.8.1
       joblib: 1.3.2
        numba: 0.58.1
  statsmodels: 0.14.0
     pmdarima: None
statsforecast: None
      tsfresh: 0.20.1
      tslearn: 0.6.3
        torch: 2.1.0
   tensorflow: None
tensorflow_probability: None

</details>

<!-- Thanks for contributing! -->


--- END ISSUE ---

Below are some code segments, each from a relevant file. One or more of these files may contain bugs.
--- BEGIN FILES ---
Path: `sktime/transformations/panel/rocket/_multirocket_multivariate.py`
Content:
```
1 import multiprocessing
2 
3 import numpy as np
4 import pandas as pd
5 
6 from sktime.transformations.base import BaseTransformer
7 
8 
9 class MultiRocketMultivariate(BaseTransformer):
10     """Multi RandOm Convolutional KErnel Transform (MultiRocket).
11 
12     MultiRocket [1]_ is uses the same set of kernels as MiniRocket on both the raw
13     series and the first order differenced series representation. It uses a different
14     set of dilations and used for each representation. In addition to percentage of
15     positive values (PPV) MultiRocket adds 3 pooling operators: Mean of Positive
16     Values (MPV); Mean of Indices of Positive Values (MIPV); and Longest Stretch of
17     Positive Values (LSPV). This version is the multivariate version.
18 
19     This transformer fits one set of paramereters per individual series,
20     and applies the transform with fitted parameter i to the i-th series in transform.
21     Vanilla use requires same number of series in fit and transform.
22 
23     To fit and transform series at the same time,
24     without an identification of fit/transform instances,
25     wrap this transformer in ``FitInTransform``,
26     from ``sktime.transformations.compose``.
27 
28     Parameters
29     ----------
30     num_kernels : int, default=6,250
31        number of random convolutional kernels. The calculated number of features is the
32        nearest multiple of n_features_per_kernel(default 4)*84=336 < 50,000
33        (2*n_features_per_kernel(default 4)*num_kernels(default 6,250)).
34     max_dilations_per_kernel : int, default=32
35         maximum number of dilations per kernel.
36     n_features_per_kernel : int, default =4
37         number of features per kernel.
38     normalise : bool, default False
39     n_jobs : int, default=1
40         The number of jobs to run in parallel for `transform`. ``-1`` means using all
41         processors.
42     random_state : None or int, default = None
43 
44     Attributes
45     ----------
46     parameter : tuple
47         parameter (dilations, num_features_per_dilation, biases) for
48         transformation of input X
49     parameter1 : tuple
50         parameter (dilations, num_features_per_dilation, biases) for
51         transformation of input X1 = np.diff(X, 1)
52 
53     See Also
54     --------
55     MultiRocketMultivariate, MiniRocket, MiniRocketMultivariate, Rocket
56 
57     References
58     ----------
59     .. [1] Tan, Chang Wei and Dempster, Angus and Bergmeir, Christoph and
60     Webb, Geoffrey I, "MultiRocket: Multiple pooling operators and transformations
61     for fast and effective time series classification",2022,
62     https://link.springer.com/article/10.1007/s10618-022-00844-1
63     https://arxiv.org/abs/2102.00457
64 
65     Examples
66     --------
67      >>> from sktime.transformations.panel.rocket import Rocket
68      >>> from sktime.datasets import load_basic_motions
69      >>> X_train, y_train = load_basic_motions(split="train") # doctest: +SKIP
70      >>> X_test, y_test = load_basic_motions(split="test") # doctest: +SKIP
71      >>> trf = MultiRocketMultivariate(num_kernels=512) # doctest: +SKIP
72      >>> trf.fit(X_train) # doctest: +SKIP
73      MultiRocketMultivariate(...)
74      >>> X_train = trf.transform(X_train) # doctest: +SKIP
75      >>> X_test = trf.transform(X_test) # doctest: +SKIP
76     """
77 
78     _tags = {
79         "univariate-only": False,
80         "fit_is_empty": False,
81         "scitype:transform-input": "Series",
82         # what is the scitype of X: Series, or Panel
83         "scitype:transform-output": "Primitives",
84         # what is the scitype of y: None (not needed), Primitives, Series, Panel
85         "scitype:instancewise": False,  # is this an instance-wise transform?
86         "X_inner_mtype": "numpy3D",  # which mtypes do _fit/_predict support for X?
87         "y_inner_mtype": "None",  # which mtypes do _fit/_predict support for X?
88         "python_dependencies": "numba",
89     }
90 
91     def __init__(
92         self,
93         num_kernels=6_250,
94         max_dilations_per_kernel=32,
95         n_features_per_kernel=4,
96         normalise=False,
97         n_jobs=1,
98         random_state=None,
99     ):
100         self.max_dilations_per_kernel = max_dilations_per_kernel
101         self.n_features_per_kernel = n_features_per_kernel
102         self.num_kernels = num_kernels
103         self.normalise = normalise
104         self.n_jobs = n_jobs
105         self.random_state = random_state if isinstance(random_state, int) else None
106 
107         self.parameter = None
108         self.parameter1 = None
109 
110         super().__init__()
111 
112     def _fit(self, X, y=None):
113         """Fit dilations and biases to input time series.
114 
115         Parameters
116         ----------
117         X : 3D np.ndarray of shape = [n_instances, n_dimensions, series_length]
118             panel of time series to transform
119         y : ignored argument for interface compatibility
120 
121         Returns
122         -------
123         self
124         """
125         if self.normalise:
126             X = (X - X.mean(axis=-1, keepdims=True)) / (
127                 X.std(axis=-1, keepdims=True) + 1e-8
128             )
129 
130         if X.shape[2] < 10:
131             # handling very short series (like PensDigit from the MTSC archive)
132             # series have to be at least a length of 10 (including differencing)
133             _X1 = np.zeros((X.shape[0], X.shape[1], 10), dtype=X.dtype)
134             _X1[:, :, : X.shape[2]] = X
135             X = _X1
136             del _X1
137 
138         X = X.astype(np.float64)
139 
140         self.parameter = self._get_parameter(X)
141         _X1 = np.diff(X, 1)
142 
143         self.parameter1 = self._get_parameter(_X1)
144 
145         return self
146 
147     def _transform(self, X, y=None):
148         """Transform input time series using random convolutional kernels.
149 
150         Parameters
151         ----------
152         X : 3D np.ndarray of shape = [n_instances, n_dimensions, series_length]
153             panel of time series to transform
154         y : ignored argument for interface compatibility
155 
156         Returns
157         -------
158         pandas DataFrame, transformed features
159         """
160         from numba import get_num_threads, set_num_threads
161 
162         from sktime.transformations.panel.rocket._multirocket_multi_numba import (
163             _transform,
164         )
165 
166         if self.normalise:
167             X = (X - X.mean(axis=-1, keepdims=True)) / (
168                 X.std(axis=-1, keepdims=True) + 1e-8
169             )
170 
171         _X1 = np.diff(X, 1)
172 
173         # change n_jobs depended on value and existing cores
174         prev_threads = get_num_threads()
175         if self.n_jobs < 1 or self.n_jobs > multiprocessing.cpu_count():
176             n_jobs = multiprocessing.cpu_count()
177         else:
178             n_jobs = self.n_jobs
179         set_num_threads(n_jobs)
180 
181         X = _transform(
182             X,
183             _X1,
184             self.parameter,
185             self.parameter1,
186             self.n_features_per_kernel,
187         )
188         X = np.nan_to_num(X)
189 
190         set_num_threads(prev_threads)
191 
192         return pd.DataFrame(X)
193 
194     def _get_parameter(self, X):
195         from sktime.transformations.panel.rocket._multirocket_multi_numba import (
196             _fit_biases,
197             _fit_dilations,
198             _quantiles,
199         )
200 
201         _, num_channels, input_length = X.shape
202 
203         num_kernels = 84
204 
205         dilations, num_features_per_dilation = _fit_dilations(
206             input_length, self.num_kernels, self.max_dilations_per_kernel
207         )
208 
209         num_features_per_kernel = np.sum(num_features_per_dilation)
210 
211         quantiles = _quantiles(num_kernels * num_features_per_kernel)
212 
213         num_dilations = len(dilations)
214         num_combinations = num_kernels * num_dilations
215 
216         max_num_channels = min(num_channels, 9)
217         max_exponent = np.log2(max_num_channels + 1)
218 
219         num_channels_per_combination = (
220             2 ** np.random.uniform(0, max_exponent, num_combinations)
221         ).astype(np.int32)
222 
223         channel_indices = np.zeros(num_channels_per_combination.sum(), dtype=np.int32)
224 
225         num_channels_start = 0
226         for combination_index in range(num_combinations):
227             num_channels_this_combination = num_channels_per_combination[
228                 combination_index
229             ]
230             num_channels_end = num_channels_start + num_channels_this_combination
231             channel_indices[num_channels_start:num_channels_end] = np.random.choice(
232                 num_channels, num_channels_this_combination, replace=False
233             )
234 
235             num_channels_start = num_channels_end
236 
237         biases = _fit_biases(
238             X,
239             num_channels_per_combination,
240             channel_indices,
241             dilations,
242             num_features_per_dilation,
243             quantiles,
244             self.random_state,
245         )
246 
247         return (
248             num_channels_per_combination,
249             channel_indices,
250             dilations,
251             num_features_per_dilation,
252             biases,
253         )
254
```
--- END FILES ---

Please first localize the bug based on the issue statement, and then generate a patch according to the `git diff` format fenced by three backticks.

Here is an example:

```diff
diff --git a/examples/server_async.py b/examples/server_async.py
--- a/examples/server_async.py
+++ b/examples/server_async.py
@@ -313,4 +313,4 @@
 
 
 if __name__ == "__main__":
-    asyncio.run(run_async_server("."), debug=True)
+    asyncio.run(run_async_server(), debug=True)
diff --git a/examples/server_sync.py b/examples/server_sync.py
--- a/examples/server_sync.py
+++ b/examples/server_sync.py
@@ -313,5 +313,5 @@
 
 
 if __name__ == "__main__":
-    server = run_sync_server(".")
+    server = run_sync_server()
     server.shutdown()

```

diff --git a/sktime/transformations/panel/rocket/_multirocket_multivariate.py b/sktime/transformations/panel/rocket/_multirocket_multivariate.py
--- a/sktime/transformations/panel/rocket/_multirocket_multivariate.py
+++ b/sktime/transformations/panel/rocket/_multirocket_multivariate.py
@@ -198,6 +198,9 @@
             _quantiles,
         )
 
+        if self.random_state is not None:
+            np.random.seed(self.random_state)
+
         _, num_channels, input_length = X.shape
 
         num_kernels = 84

{"golden_diff": "diff --git a/sktime/transformations/panel/rocket/_multirocket_multivariate.py b/sktime/transformations/panel/rocket/_multirocket_multivariate.py\n--- a/sktime/transformations/panel/rocket/_multirocket_multivariate.py\n+++ b/sktime/transformations/panel/rocket/_multirocket_multivariate.py\n@@ -198,6 +198,9 @@\n             _quantiles,\n         )\n \n+        if self.random_state is not None:\n+            np.random.seed(self.random_state)\n+\n         _, num_channels, input_length = X.shape\n \n         num_kernels = 84\n", "issue": "[BUG] Irreproducible results with `MultiRocketMultivariate`\n`random_state` does guarantee the same results for each run.\r\n\r\n```python\r\nrng = np.random.default_rng()\r\n\r\nX = pd.DataFrame([\r\n    pd.Series([\r\n        pd.Series(rng.integers(0, 10, 100)).astype(float),\r\n        pd.Series(rng.integers(0, 10, 100)).astype(float),\r\n    ]),\r\n    pd.Series([\r\n        pd.Series(rng.integers(0, 10, 100)).astype(float),\r\n        pd.Series(rng.integers(0, 10, 100)).astype(float),\r\n    ]),\r\n])\r\n\r\nMultiRocketMultivariate(random_state=42, num_kernels=84).fit_transform(X) - MultiRocketMultivariate(random_state=42, num_kernels=84).fit_transform(X)\r\n```\r\n\r\nThe output should always be a `DataFrame` of zeros, but this is not the case.\r\n\r\n<details>\r\n\r\n<!--\r\nPlease run the following code snippet and paste the output here:\r\n\r\nfrom sktime import show_versions; show_versions()\r\n-->\r\n\r\nSystem:\r\n    python: 3.9.6 (default, Aug 11 2023, 19:44:49)  [Clang 15.0.0 (clang-1500.0.40.1)]\r\nexecutable: /Users/temp/sktime/venv/bin/python\r\n   machine: macOS-14.1.2-arm64-arm-64bit\r\n\r\nPython dependencies:\r\n          pip: 23.3.1\r\n       sktime: 0.25.0\r\n      sklearn: 1.3.2\r\n       skbase: 0.4.6\r\n        numpy: 1.26.1\r\n        scipy: 1.11.3\r\n       pandas: 2.1.4\r\n   matplotlib: 3.8.1\r\n       joblib: 1.3.2\r\n        numba: 0.58.1\r\n  statsmodels: 0.14.0\r\n     pmdarima: None\r\nstatsforecast: None\r\n      tsfresh: 0.20.1\r\n      tslearn: 0.6.3\r\n        torch: 2.1.0\r\n   tensorflow: None\r\ntensorflow_probability: None\r\n\r\n</details>\r\n\r\n<!-- Thanks for contributing! -->\r\n\n", "before_files": [{"content": "import multiprocessing\n\nimport numpy as np\nimport pandas as pd\n\nfrom sktime.transformations.base import BaseTransformer\n\n\nclass MultiRocketMultivariate(BaseTransformer):\n    \"\"\"Multi RandOm Convolutional KErnel Transform (MultiRocket).\n\n    MultiRocket [1]_ is uses the same set of kernels as MiniRocket on both the raw\n    series and the first order differenced series representation. It uses a different\n    set of dilations and used for each representation. In addition to percentage of\n    positive values (PPV) MultiRocket adds 3 pooling operators: Mean of Positive\n    Values (MPV); Mean of Indices of Positive Values (MIPV); and Longest Stretch of\n    Positive Values (LSPV). This version is the multivariate version.\n\n    This transformer fits one set of paramereters per individual series,\n    and applies the transform with fitted parameter i to the i-th series in transform.\n    Vanilla use requires same number of series in fit and transform.\n\n    To fit and transform series at the same time,\n    without an identification of fit/transform instances,\n    wrap this transformer in ``FitInTransform``,\n    from ``sktime.transformations.compose``.\n\n    Parameters\n    ----------\n    num_kernels : int, default=6,250\n       number of random convolutional kernels. The calculated number of features is the\n       nearest multiple of n_features_per_kernel(default 4)*84=336 < 50,000\n       (2*n_features_per_kernel(default 4)*num_kernels(default 6,250)).\n    max_dilations_per_kernel : int, default=32\n        maximum number of dilations per kernel.\n    n_features_per_kernel : int, default =4\n        number of features per kernel.\n    normalise : bool, default False\n    n_jobs : int, default=1\n        The number of jobs to run in parallel for `transform`. ``-1`` means using all\n        processors.\n    random_state : None or int, default = None\n\n    Attributes\n    ----------\n    parameter : tuple\n        parameter (dilations, num_features_per_dilation, biases) for\n        transformation of input X\n    parameter1 : tuple\n        parameter (dilations, num_features_per_dilation, biases) for\n        transformation of input X1 = np.diff(X, 1)\n\n    See Also\n    --------\n    MultiRocketMultivariate, MiniRocket, MiniRocketMultivariate, Rocket\n\n    References\n    ----------\n    .. [1] Tan, Chang Wei and Dempster, Angus and Bergmeir, Christoph and\n    Webb, Geoffrey I, \"MultiRocket: Multiple pooling operators and transformations\n    for fast and effective time series classification\",2022,\n    https://link.springer.com/article/10.1007/s10618-022-00844-1\n    https://arxiv.org/abs/2102.00457\n\n    Examples\n    --------\n     >>> from sktime.transformations.panel.rocket import Rocket\n     >>> from sktime.datasets import load_basic_motions\n     >>> X_train, y_train = load_basic_motions(split=\"train\") # doctest: +SKIP\n     >>> X_test, y_test = load_basic_motions(split=\"test\") # doctest: +SKIP\n     >>> trf = MultiRocketMultivariate(num_kernels=512) # doctest: +SKIP\n     >>> trf.fit(X_train) # doctest: +SKIP\n     MultiRocketMultivariate(...)\n     >>> X_train = trf.transform(X_train) # doctest: +SKIP\n     >>> X_test = trf.transform(X_test) # doctest: +SKIP\n    \"\"\"\n\n    _tags = {\n        \"univariate-only\": False,\n        \"fit_is_empty\": False,\n        \"scitype:transform-input\": \"Series\",\n        # what is the scitype of X: Series, or Panel\n        \"scitype:transform-output\": \"Primitives\",\n        # what is the scitype of y: None (not needed), Primitives, Series, Panel\n        \"scitype:instancewise\": False,  # is this an instance-wise transform?\n        \"X_inner_mtype\": \"numpy3D\",  # which mtypes do _fit/_predict support for X?\n        \"y_inner_mtype\": \"None\",  # which mtypes do _fit/_predict support for X?\n        \"python_dependencies\": \"numba\",\n    }\n\n    def __init__(\n        self,\n        num_kernels=6_250,\n        max_dilations_per_kernel=32,\n        n_features_per_kernel=4,\n        normalise=False,\n        n_jobs=1,\n        random_state=None,\n    ):\n        self.max_dilations_per_kernel = max_dilations_per_kernel\n        self.n_features_per_kernel = n_features_per_kernel\n        self.num_kernels = num_kernels\n        self.normalise = normalise\n        self.n_jobs = n_jobs\n        self.random_state = random_state if isinstance(random_state, int) else None\n\n        self.parameter = None\n        self.parameter1 = None\n\n        super().__init__()\n\n    def _fit(self, X, y=None):\n        \"\"\"Fit dilations and biases to input time series.\n\n        Parameters\n        ----------\n        X : 3D np.ndarray of shape = [n_instances, n_dimensions, series_length]\n            panel of time series to transform\n        y : ignored argument for interface compatibility\n\n        Returns\n        -------\n        self\n        \"\"\"\n        if self.normalise:\n            X = (X - X.mean(axis=-1, keepdims=True)) / (\n                X.std(axis=-1, keepdims=True) + 1e-8\n            )\n\n        if X.shape[2] < 10:\n            # handling very short series (like PensDigit from the MTSC archive)\n            # series have to be at least a length of 10 (including differencing)\n            _X1 = np.zeros((X.shape[0], X.shape[1], 10), dtype=X.dtype)\n            _X1[:, :, : X.shape[2]] = X\n            X = _X1\n            del _X1\n\n        X = X.astype(np.float64)\n\n        self.parameter = self._get_parameter(X)\n        _X1 = np.diff(X, 1)\n\n        self.parameter1 = self._get_parameter(_X1)\n\n        return self\n\n    def _transform(self, X, y=None):\n        \"\"\"Transform input time series using random convolutional kernels.\n\n        Parameters\n        ----------\n        X : 3D np.ndarray of shape = [n_instances, n_dimensions, series_length]\n            panel of time series to transform\n        y : ignored argument for interface compatibility\n\n        Returns\n        -------\n        pandas DataFrame, transformed features\n        \"\"\"\n        from numba import get_num_threads, set_num_threads\n\n        from sktime.transformations.panel.rocket._multirocket_multi_numba import (\n            _transform,\n        )\n\n        if self.normalise:\n            X = (X - X.mean(axis=-1, keepdims=True)) / (\n                X.std(axis=-1, keepdims=True) + 1e-8\n            )\n\n        _X1 = np.diff(X, 1)\n\n        # change n_jobs depended on value and existing cores\n        prev_threads = get_num_threads()\n        if self.n_jobs < 1 or self.n_jobs > multiprocessing.cpu_count():\n            n_jobs = multiprocessing.cpu_count()\n        else:\n            n_jobs = self.n_jobs\n        set_num_threads(n_jobs)\n\n        X = _transform(\n            X,\n            _X1,\n            self.parameter,\n            self.parameter1,\n            self.n_features_per_kernel,\n        )\n        X = np.nan_to_num(X)\n\n        set_num_threads(prev_threads)\n\n        return pd.DataFrame(X)\n\n    def _get_parameter(self, X):\n        from sktime.transformations.panel.rocket._multirocket_multi_numba import (\n            _fit_biases,\n            _fit_dilations,\n            _quantiles,\n        )\n\n        _, num_channels, input_length = X.shape\n\n        num_kernels = 84\n\n        dilations, num_features_per_dilation = _fit_dilations(\n            input_length, self.num_kernels, self.max_dilations_per_kernel\n        )\n\n        num_features_per_kernel = np.sum(num_features_per_dilation)\n\n        quantiles = _quantiles(num_kernels * num_features_per_kernel)\n\n        num_dilations = len(dilations)\n        num_combinations = num_kernels * num_dilations\n\n        max_num_channels = min(num_channels, 9)\n        max_exponent = np.log2(max_num_channels + 1)\n\n        num_channels_per_combination = (\n            2 ** np.random.uniform(0, max_exponent, num_combinations)\n        ).astype(np.int32)\n\n        channel_indices = np.zeros(num_channels_per_combination.sum(), dtype=np.int32)\n\n        num_channels_start = 0\n        for combination_index in range(num_combinations):\n            num_channels_this_combination = num_channels_per_combination[\n                combination_index\n            ]\n            num_channels_end = num_channels_start + num_channels_this_combination\n            channel_indices[num_channels_start:num_channels_end] = np.random.choice(\n                num_channels, num_channels_this_combination, replace=False\n            )\n\n            num_channels_start = num_channels_end\n\n        biases = _fit_biases(\n            X,\n            num_channels_per_combination,\n            channel_indices,\n            dilations,\n            num_features_per_dilation,\n            quantiles,\n            self.random_state,\n        )\n\n        return (\n            num_channels_per_combination,\n            channel_indices,\n            dilations,\n            num_features_per_dilation,\n            biases,\n        )\n", "path": "sktime/transformations/panel/rocket/_multirocket_multivariate.py"}], "after_files": [{"content": "import multiprocessing\n\nimport numpy as np\nimport pandas as pd\n\nfrom sktime.transformations.base import BaseTransformer\n\n\nclass MultiRocketMultivariate(BaseTransformer):\n    \"\"\"Multi RandOm Convolutional KErnel Transform (MultiRocket).\n\n    MultiRocket [1]_ is uses the same set of kernels as MiniRocket on both the raw\n    series and the first order differenced series representation. It uses a different\n    set of dilations and used for each representation. In addition to percentage of\n    positive values (PPV) MultiRocket adds 3 pooling operators: Mean of Positive\n    Values (MPV); Mean of Indices of Positive Values (MIPV); and Longest Stretch of\n    Positive Values (LSPV). This version is the multivariate version.\n\n    This transformer fits one set of paramereters per individual series,\n    and applies the transform with fitted parameter i to the i-th series in transform.\n    Vanilla use requires same number of series in fit and transform.\n\n    To fit and transform series at the same time,\n    without an identification of fit/transform instances,\n    wrap this transformer in ``FitInTransform``,\n    from ``sktime.transformations.compose``.\n\n    Parameters\n    ----------\n    num_kernels : int, default=6,250\n       number of random convolutional kernels. The calculated number of features is the\n       nearest multiple of n_features_per_kernel(default 4)*84=336 < 50,000\n       (2*n_features_per_kernel(default 4)*num_kernels(default 6,250)).\n    max_dilations_per_kernel : int, default=32\n        maximum number of dilations per kernel.\n    n_features_per_kernel : int, default =4\n        number of features per kernel.\n    normalise : bool, default False\n    n_jobs : int, default=1\n        The number of jobs to run in parallel for `transform`. ``-1`` means using all\n        processors.\n    random_state : None or int, default = None\n\n    Attributes\n    ----------\n    parameter : tuple\n        parameter (dilations, num_features_per_dilation, biases) for\n        transformation of input X\n    parameter1 : tuple\n        parameter (dilations, num_features_per_dilation, biases) for\n        transformation of input X1 = np.diff(X, 1)\n\n    See Also\n    --------\n    MultiRocketMultivariate, MiniRocket, MiniRocketMultivariate, Rocket\n\n    References\n    ----------\n    .. [1] Tan, Chang Wei and Dempster, Angus and Bergmeir, Christoph and\n    Webb, Geoffrey I, \"MultiRocket: Multiple pooling operators and transformations\n    for fast and effective time series classification\",2022,\n    https://link.springer.com/article/10.1007/s10618-022-00844-1\n    https://arxiv.org/abs/2102.00457\n\n    Examples\n    --------\n     >>> from sktime.transformations.panel.rocket import Rocket\n     >>> from sktime.datasets import load_basic_motions\n     >>> X_train, y_train = load_basic_motions(split=\"train\") # doctest: +SKIP\n     >>> X_test, y_test = load_basic_motions(split=\"test\") # doctest: +SKIP\n     >>> trf = MultiRocketMultivariate(num_kernels=512) # doctest: +SKIP\n     >>> trf.fit(X_train) # doctest: +SKIP\n     MultiRocketMultivariate(...)\n     >>> X_train = trf.transform(X_train) # doctest: +SKIP\n     >>> X_test = trf.transform(X_test) # doctest: +SKIP\n    \"\"\"\n\n    _tags = {\n        \"univariate-only\": False,\n        \"fit_is_empty\": False,\n        \"scitype:transform-input\": \"Series\",\n        # what is the scitype of X: Series, or Panel\n        \"scitype:transform-output\": \"Primitives\",\n        # what is the scitype of y: None (not needed), Primitives, Series, Panel\n        \"scitype:instancewise\": False,  # is this an instance-wise transform?\n        \"X_inner_mtype\": \"numpy3D\",  # which mtypes do _fit/_predict support for X?\n        \"y_inner_mtype\": \"None\",  # which mtypes do _fit/_predict support for X?\n        \"python_dependencies\": \"numba\",\n    }\n\n    def __init__(\n        self,\n        num_kernels=6_250,\n        max_dilations_per_kernel=32,\n        n_features_per_kernel=4,\n        normalise=False,\n        n_jobs=1,\n        random_state=None,\n    ):\n        self.max_dilations_per_kernel = max_dilations_per_kernel\n        self.n_features_per_kernel = n_features_per_kernel\n        self.num_kernels = num_kernels\n        self.normalise = normalise\n        self.n_jobs = n_jobs\n        self.random_state = random_state if isinstance(random_state, int) else None\n\n        self.parameter = None\n        self.parameter1 = None\n\n        super().__init__()\n\n    def _fit(self, X, y=None):\n        \"\"\"Fit dilations and biases to input time series.\n\n        Parameters\n        ----------\n        X : 3D np.ndarray of shape = [n_instances, n_dimensions, series_length]\n            panel of time series to transform\n        y : ignored argument for interface compatibility\n\n        Returns\n        -------\n        self\n        \"\"\"\n        if self.normalise:\n            X = (X - X.mean(axis=-1, keepdims=True)) / (\n                X.std(axis=-1, keepdims=True) + 1e-8\n            )\n\n        if X.shape[2] < 10:\n            # handling very short series (like PensDigit from the MTSC archive)\n            # series have to be at least a length of 10 (including differencing)\n            _X1 = np.zeros((X.shape[0], X.shape[1], 10), dtype=X.dtype)\n            _X1[:, :, : X.shape[2]] = X\n            X = _X1\n            del _X1\n\n        X = X.astype(np.float64)\n\n        self.parameter = self._get_parameter(X)\n        _X1 = np.diff(X, 1)\n\n        self.parameter1 = self._get_parameter(_X1)\n\n        return self\n\n    def _transform(self, X, y=None):\n        \"\"\"Transform input time series using random convolutional kernels.\n\n        Parameters\n        ----------\n        X : 3D np.ndarray of shape = [n_instances, n_dimensions, series_length]\n            panel of time series to transform\n        y : ignored argument for interface compatibility\n\n        Returns\n        -------\n        pandas DataFrame, transformed features\n        \"\"\"\n        from numba import get_num_threads, set_num_threads\n\n        from sktime.transformations.panel.rocket._multirocket_multi_numba import (\n            _transform,\n        )\n\n        if self.normalise:\n            X = (X - X.mean(axis=-1, keepdims=True)) / (\n                X.std(axis=-1, keepdims=True) + 1e-8\n            )\n\n        _X1 = np.diff(X, 1)\n\n        # change n_jobs depended on value and existing cores\n        prev_threads = get_num_threads()\n        if self.n_jobs < 1 or self.n_jobs > multiprocessing.cpu_count():\n            n_jobs = multiprocessing.cpu_count()\n        else:\n            n_jobs = self.n_jobs\n        set_num_threads(n_jobs)\n\n        X = _transform(\n            X,\n            _X1,\n            self.parameter,\n            self.parameter1,\n            self.n_features_per_kernel,\n        )\n        X = np.nan_to_num(X)\n\n        set_num_threads(prev_threads)\n\n        return pd.DataFrame(X)\n\n    def _get_parameter(self, X):\n        from sktime.transformations.panel.rocket._multirocket_multi_numba import (\n            _fit_biases,\n            _fit_dilations,\n            _quantiles,\n        )\n\n        if self.random_state is not None:\n            np.random.seed(self.random_state)\n\n        _, num_channels, input_length = X.shape\n\n        num_kernels = 84\n\n        dilations, num_features_per_dilation = _fit_dilations(\n            input_length, self.num_kernels, self.max_dilations_per_kernel\n        )\n\n        num_features_per_kernel = np.sum(num_features_per_dilation)\n\n        quantiles = _quantiles(num_kernels * num_features_per_kernel)\n\n        num_dilations = len(dilations)\n        num_combinations = num_kernels * num_dilations\n\n        max_num_channels = min(num_channels, 9)\n        max_exponent = np.log2(max_num_channels + 1)\n\n        num_channels_per_combination = (\n            2 ** np.random.uniform(0, max_exponent, num_combinations)\n        ).astype(np.int32)\n\n        channel_indices = np.zeros(num_channels_per_combination.sum(), dtype=np.int32)\n\n        num_channels_start = 0\n        for combination_index in range(num_combinations):\n            num_channels_this_combination = num_channels_per_combination[\n                combination_index\n            ]\n            num_channels_end = num_channels_start + num_channels_this_combination\n            channel_indices[num_channels_start:num_channels_end] = np.random.choice(\n                num_channels, num_channels_this_combination, replace=False\n            )\n\n            num_channels_start = num_channels_end\n\n        biases = _fit_biases(\n            X,\n            num_channels_per_combination,\n            channel_indices,\n            dilations,\n            num_features_per_dilation,\n            quantiles,\n            self.random_state,\n        )\n\n        return (\n            num_channels_per_combination,\n            channel_indices,\n            dilations,\n            num_features_per_dilation,\n            biases,\n        )\n", "path": "sktime/transformations/panel/rocket/_multirocket_multivariate.py"}]}