You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@arrow.apache.org by ke...@apache.org on 2023/08/04 19:20:03 UTC

[arrow] branch main updated: GH-36984: [MATLAB] Create `arrow.recordbatch` convenience constructor function (#37025)

This is an automated email from the ASF dual-hosted git repository.

kevingurney pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/arrow.git


The following commit(s) were added to refs/heads/main by this push:
     new 19d0daf40c GH-36984: [MATLAB] Create `arrow.recordbatch` convenience constructor function (#37025)
19d0daf40c is described below

commit 19d0daf40c2db5164a6bfefc91019253d8db7157
Author: sgilmore10 <74...@users.noreply.github.com>
AuthorDate: Fri Aug 4 15:19:57 2023 -0400

    GH-36984: [MATLAB] Create `arrow.recordbatch` convenience constructor function (#37025)
    
    ### Rationale for this change
    For parity with how `arrow.array.Array` objects are constructed (i.e. via `arrow.array`), we should create a construction function called `arrow.recordbatch()` for `arrow.tabular.RecordBatch`:
    
    ```matlab
    >> t = table(["A"; "B"; "C"], [1; 2; 3])
    
    t =
    
      3×2 table
    
        Var1    Var2
        ____    ____
    
        "A"      1
        "B"      2
        "C"      3
    
    >> rb = arrow.recordbatch(t)
    
    rb =
    
    Var1:   [
        "A",
        "B",
        "C"
      ]
    Var2:   [
        1,
        2,
        3
      ]
    
    >> class(rb)
    
    ans =
    
        'arrow.tabular.RecordBatch'
    ```
    
    The `arrow.tabular.RecordBatch` constructor will accept a scalar `libmexclass.proxy.Proxy` object instead of a MATLAB `table` (although, client code is not expected to call the constructor directly - similar to the other classes).
    
    ### What changes are included in this PR?
    
    1. Added the convenience constructor function  `arrow.recordbatch()`. It accepts a MATLAB `table` as input.
    2. Modified `arrow.tabular.RecordBatch`'s constructor to expect a scalar `libmexclass.proxy.Proxy` object as input instead of a `table`.
    
    ### Are these changes tested?
    
    Yes, updated the test cases in `tRecordBatch.m` to use the new convenience constructor  `arrow.recordbatch()` .
    
    ### Are there any user-facing changes?
    
    Yes, users are now encouraged to use `arrow.recordbatch()` when constructing a record batch from a MATLAB `table` instead of  `arrow.tabular.RecordBatch`'s constructor.
    
    * Closes: #36984
    
    Authored-by: Sarah Gilmore <sg...@mathworks.com>
    Signed-off-by: Kevin Gurney <kg...@mathworks.com>
---
 .../matlab/+arrow/+tabular/+internal/decompose.m   | 27 +++++++++++
 .../+arrow/+tabular/+internal/getArrayProxyIDs.m   | 26 +++++++++++
 matlab/src/matlab/+arrow/+tabular/RecordBatch.m    | 53 +++-------------------
 matlab/src/matlab/+arrow/recordbatch.m             | 31 +++++++++++++
 matlab/test/arrow/tabular/tRecordBatch.m           | 22 ++++-----
 5 files changed, 102 insertions(+), 57 deletions(-)

diff --git a/matlab/src/matlab/+arrow/+tabular/+internal/decompose.m b/matlab/src/matlab/+arrow/+tabular/+internal/decompose.m
new file mode 100644
index 0000000000..2d8ec58130
--- /dev/null
+++ b/matlab/src/matlab/+arrow/+tabular/+internal/decompose.m
@@ -0,0 +1,27 @@
+%DECOMPOSE Decompose the input MATLAB table input a cell array of 
+% equivalent arrow.array.Array instances.
+
+% Licensed to the Apache Software Foundation (ASF) under one or more
+% contributor license agreements.  See the NOTICE file distributed with
+% this work for additional information regarding copyright ownership.
+% The ASF licenses this file to you under the Apache License, Version
+% 2.0 (the "License"); you may not use this file except in compliance
+% with the License.  You may obtain a copy of the License at
+%
+%   http://www.apache.org/licenses/LICENSE-2.0
+%
+% Unless required by applicable law or agreed to in writing, software
+% distributed under the License is distributed on an "AS IS" BASIS,
+% WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+% implied.  See the License for the specific language governing
+% permissions and limitations under the License.
+function arrowArrays = decompose(T)
+    numColumns = width(T);
+    arrowArrays = cell(1, numColumns);
+
+    % Convert each MATLAB array into a corresponding
+    % arrow.array.Array.
+    for ii = 1:numColumns
+        arrowArrays{ii} = arrow.array(T{:, ii});
+    end
+end
\ No newline at end of file
diff --git a/matlab/src/matlab/+arrow/+tabular/+internal/getArrayProxyIDs.m b/matlab/src/matlab/+arrow/+tabular/+internal/getArrayProxyIDs.m
new file mode 100644
index 0000000000..8a1f881589
--- /dev/null
+++ b/matlab/src/matlab/+arrow/+tabular/+internal/getArrayProxyIDs.m
@@ -0,0 +1,26 @@
+%GETARRAYPROXYIDS Extract the Proxy IDs underlying a cell array of 
+% arrow.array.Array instances.
+
+% Licensed to the Apache Software Foundation (ASF) under one or more
+% contributor license agreements.  See the NOTICE file distributed with
+% this work for additional information regarding copyright ownership.
+% The ASF licenses this file to you under the Apache License, Version
+% 2.0 (the "License"); you may not use this file except in compliance
+% with the License.  You may obtain a copy of the License at
+%
+%   http://www.apache.org/licenses/LICENSE-2.0
+%
+% Unless required by applicable law or agreed to in writing, software
+% distributed under the License is distributed on an "AS IS" BASIS,
+% WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+% implied.  See the License for the specific language governing
+% permissions and limitations under the License.
+function proxyIDs = getArrayProxyIDs(arrowArrays)
+    proxyIDs = zeros(1, numel(arrowArrays), "uint64");
+
+    % Convert each MATLAB array into a corresponding
+    % arrow.array.Array.
+    for ii = 1:numel(arrowArrays)
+        proxyIDs(ii) = arrowArrays{ii}.Proxy.ID;
+    end
+end
\ No newline at end of file
diff --git a/matlab/src/matlab/+arrow/+tabular/RecordBatch.m b/matlab/src/matlab/+arrow/+tabular/RecordBatch.m
index 796f2f0c7a..0d002797f0 100644
--- a/matlab/src/matlab/+arrow/+tabular/RecordBatch.m
+++ b/matlab/src/matlab/+arrow/+tabular/RecordBatch.m
@@ -28,6 +28,13 @@ classdef RecordBatch < matlab.mixin.CustomDisplay & ...
     end
 
     methods
+        function obj = RecordBatch(proxy)
+            arguments
+                proxy(1, 1) libmexclass.proxy.Proxy {validate(proxy, "arrow.tabular.proxy.RecordBatch")}
+            end
+            import arrow.internal.proxy.validate
+            obj.Proxy = proxy;
+        end
 
         function numColumns = get.NumColumns(obj)
             numColumns = obj.Proxy.numColumns();
@@ -51,15 +58,6 @@ classdef RecordBatch < matlab.mixin.CustomDisplay & ...
             end
         end
 
-        function obj = RecordBatch(T)
-            arrowArrays = arrow.tabular.RecordBatch.decompose(T);
-            columnNames = string(T.Properties.VariableNames);
-            arrayProxyIDs = arrow.tabular.RecordBatch.getArrowProxyIDs(arrowArrays);
-            opts = struct("ArrayProxyIDs", arrayProxyIDs, ...
-                          "ColumnNames", columnNames);
-            obj.Proxy = libmexclass.proxy.Proxy("Name", "arrow.tabular.proxy.RecordBatch", "ConstructorArguments", {opts});
-        end
-
         function T = table(obj)
             numColumns = obj.NumColumns;
             matlabArrays = cell(1, numColumns);
@@ -78,41 +76,6 @@ classdef RecordBatch < matlab.mixin.CustomDisplay & ...
         function T = toMATLAB(obj)
             T = obj.table();
         end
-        
-    end
-
-    methods (Static)
-
-        function arrowArrays = decompose(T)
-            % Decompose the input MATLAB table
-            % input a cell array of equivalent arrow.array.Array
-            % instances.
-            arguments
-                T table
-            end
-
-            numColumns = width(T);
-            arrowArrays = cell(1, numColumns);
-
-            % Convert each MATLAB array into a corresponding
-            % arrow.array.Array.
-            for ii = 1:numColumns
-                arrowArrays{ii} = arrow.array(T{:, ii});
-            end
-        end
-
-        function proxyIDs = getArrowProxyIDs(arrowArrays)
-            % Extract the Proxy IDs underlying a cell array of 
-            % arrow.array.Array instances.
-            proxyIDs = zeros(1, numel(arrowArrays), "uint64");
-
-            % Convert each MATLAB array into a corresponding
-            % arrow.array.Array.
-            for ii = 1:numel(arrowArrays)
-                proxyIDs(ii) = arrowArrays{ii}.Proxy.ID;
-            end
-        end
-
     end
 
     methods (Access = private)
@@ -126,6 +89,4 @@ classdef RecordBatch < matlab.mixin.CustomDisplay & ...
             disp(obj.toString());
         end
     end
-
 end
-
diff --git a/matlab/src/matlab/+arrow/recordbatch.m b/matlab/src/matlab/+arrow/recordbatch.m
new file mode 100644
index 0000000000..1fb25347f1
--- /dev/null
+++ b/matlab/src/matlab/+arrow/recordbatch.m
@@ -0,0 +1,31 @@
+%RECORDBATCH Creates an arrow.tabular.RecordBatch from a table.
+
+% Licensed to the Apache Software Foundation (ASF) under one or more
+% contributor license agreements.  See the NOTICE file distributed with
+% this work for additional information regarding copyright ownership.
+% The ASF licenses this file to you under the Apache License, Version
+% 2.0 (the "License"); you may not use this file except in compliance
+% with the License.  You may obtain a copy of the License at
+%
+%   http://www.apache.org/licenses/LICENSE-2.0
+%
+% Unless required by applicable law or agreed to in writing, software
+% distributed under the License is distributed on an "AS IS" BASIS,
+% WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
+% implied.  See the License for the specific language governing
+% permissions and limitations under the License.
+function rb = recordbatch(T)
+    arguments
+        T table
+    end
+
+    arrowArrays = arrow.tabular.internal.decompose(T);
+    arrayProxyIDs = arrow.tabular.internal.getArrayProxyIDs(arrowArrays);
+
+    columnNames = string(T.Properties.VariableNames);
+    args = struct(ArrayProxyIDs=arrayProxyIDs, ColumnNames=columnNames);
+    proxyName = "arrow.tabular.proxy.RecordBatch";
+    proxy = arrow.internal.proxy.create(proxyName, args);
+
+    rb = arrow.tabular.RecordBatch(proxy);
+end
diff --git a/matlab/test/arrow/tabular/tRecordBatch.m b/matlab/test/arrow/tabular/tRecordBatch.m
index 78bfe7c090..025f15320a 100644
--- a/matlab/test/arrow/tabular/tRecordBatch.m
+++ b/matlab/test/arrow/tabular/tRecordBatch.m
@@ -20,7 +20,7 @@ classdef tRecordBatch < matlab.unittest.TestCase
 
         function Basic(tc)
             T = table([1, 2, 3]');
-            arrowRecordBatch = arrow.tabular.RecordBatch(T);
+            arrowRecordBatch = arrow.recordbatch(T);
             className = string(class(arrowRecordBatch));
             tc.verifyEqual(className, "arrow.tabular.RecordBatch");
         end
@@ -40,7 +40,7 @@ classdef tRecordBatch < matlab.unittest.TestCase
                               double ([1, 2, 3]'), ...
                               string (["A", "B", "C"]'), ...
                               datetime(2023, 6, 28) + days(0:2)');
-            arrowRecordBatch = arrow.tabular.RecordBatch(TOriginal);
+            arrowRecordBatch = arrow.recordbatch(TOriginal);
             TConverted = arrowRecordBatch.toMATLAB();
             tc.verifyEqual(TOriginal, TConverted);
             for ii = 1:arrowRecordBatch.NumColumns
@@ -53,14 +53,14 @@ classdef tRecordBatch < matlab.unittest.TestCase
 
         function ToMATLAB(tc)
             TOriginal = table([1, 2, 3]');
-            arrowRecordBatch = arrow.tabular.RecordBatch(TOriginal);
+            arrowRecordBatch = arrow.recordbatch(TOriginal);
             TConverted = arrowRecordBatch.toMATLAB();
             tc.verifyEqual(TOriginal, TConverted);
         end
 
         function Table(tc)
             TOriginal = table([1, 2, 3]');
-            arrowRecordBatch = arrow.tabular.RecordBatch(TOriginal);
+            arrowRecordBatch = arrow.recordbatch(TOriginal);
             TConverted = table(arrowRecordBatch);
             tc.verifyEqual(TOriginal, TConverted);
         end
@@ -68,7 +68,7 @@ classdef tRecordBatch < matlab.unittest.TestCase
         function ColumnNames(tc)
             columnNames = ["A", "B", "C"];
             TOriginal = table(1, 2, 3, VariableNames=columnNames);
-            arrowRecordBatch = arrow.tabular.RecordBatch(TOriginal);
+            arrowRecordBatch = arrow.recordbatch(TOriginal);
             tc.verifyEqual(arrowRecordBatch.ColumnNames, columnNames);
         end
 
@@ -77,7 +77,7 @@ classdef tRecordBatch < matlab.unittest.TestCase
 
             for nc = numColumns
                 T = array2table(ones(1, nc));
-                arrowRecordBatch = arrow.tabular.RecordBatch(T);
+                arrowRecordBatch = arrow.recordbatch(T);
                 tc.verifyEqual(arrowRecordBatch.NumColumns, nc);
             end
         end
@@ -88,7 +88,7 @@ classdef tRecordBatch < matlab.unittest.TestCase
             mango = "🥭";
             columnNames = [smiley, tree, mango];
             TOriginal = table(1, 2, 3, VariableNames=columnNames);
-            arrowRecordBatch = arrow.tabular.RecordBatch(TOriginal);
+            arrowRecordBatch = arrow.recordbatch(TOriginal);
             tc.verifyEqual(arrowRecordBatch.ColumnNames, columnNames);
             TConverted = arrowRecordBatch.toMATLAB();
             tc.verifyEqual(TOriginal, TConverted);
@@ -96,28 +96,28 @@ classdef tRecordBatch < matlab.unittest.TestCase
 
         function EmptyTable(tc)
             TOriginal = table();
-            arrowRecordBatch = arrow.tabular.RecordBatch(TOriginal);
+            arrowRecordBatch = arrow.recordbatch(TOriginal);
             TConverted = arrowRecordBatch.toMATLAB();
             tc.verifyEqual(TOriginal, TConverted);
         end
 
         function EmptyRecordBatchColumnIndexError(tc)
             TOriginal = table();
-            arrowRecordBatch = arrow.tabular.RecordBatch(TOriginal);
+            arrowRecordBatch = arrow.recordbatch(TOriginal);
             fcn = @() arrowRecordBatch.column(1);
             tc.verifyError(fcn, "arrow:tabular:recordbatch:NumericIndexWithEmptyRecordBatch");
         end
 
         function InvalidNumericIndexError(tc)
             TOriginal = table(1, 2, 3);
-            arrowRecordBatch = arrow.tabular.RecordBatch(TOriginal);
+            arrowRecordBatch = arrow.recordbatch(TOriginal);
             fcn = @() arrowRecordBatch.column(4);
             tc.verifyError(fcn, "arrow:tabular:recordbatch:InvalidNumericColumnIndex");
         end
 
         function UnsupportedColumnIndexType(tc)
             TOriginal = table(1, 2, 3);
-            arrowRecordBatch = arrow.tabular.RecordBatch(TOriginal);
+            arrowRecordBatch = arrow.recordbatch(TOriginal);
             fcn = @() arrowRecordBatch.column(datetime(2022, 1, 3));
             tc.verifyError(fcn, "arrow:tabular:recordbatch:UnsupportedColumnIndexType");
         end