我正在构建一套函数来处理多维数组数据结构,我希望能够定义数组的任意切片,这样我就可以实现两个任意矩阵(又称Tensors或nd数组)的广义内积.
一个APL论文我看了(老实说,我无法找到它-我已经看了这么多)定义的矩阵产品上左矩阵X,其尺寸A;B;C;D;E;F和右矩阵Y,尺寸G;H;I;J;K,其中F==G作为
Z <- X +.× Y
Z[A;B;C;D;E;H;I;J;K] <- +/ X[A;B;C;D;E;*] × Y[*;H;I;J;K]
Run Code Online (Sandbox Code Playgroud)
其中+/是和的和,并且×将元素逐个元素应用于两个相同长度的向量.
所以我需要左边的"行"切片和右边的"列"切片.我当然可以使用转置,然后使用"行"切片来模拟"列"切片,但我宁愿更优雅地做.
维基百科关于切片的文章引出了关于涂料载体的存根,这似乎是我正在寻找的奇迹治疗,但是没有太多可以继续下去.
如何使用涂料矢量来实现任意切片?
(很久以后我注意到了一个有一些细节的数组的Stride.)
c transpose slice multidimensional-array matrix-multiplication
典型的1-D数组可以在声明中静态或自动分配.
enum { n=100 };
int arr1[n];
Run Code Online (Sandbox Code Playgroud)
或者通过指针动态分配和访问.
int *arr1m=malloc(n*sizeof*arr1m);
int *arr1c=calloc(n, sizeof*arr1c);
Run Code Online (Sandbox Code Playgroud)
这两种样式都使用相同的语法访问元素.
int i = n/2;
arr1[i] = arr1c[i] = arr1m[i] = 42;
Run Code Online (Sandbox Code Playgroud)
但是当你添加第二个维度时,需要花费一些力气来实现相同的语法.
int arr2[n][n];
int *arr2c=calloc(n*n,sizeof*arr2c);
arr2[5][5] = arr2c[5*n+5] = 23;
Run Code Online (Sandbox Code Playgroud)
如果您将其构造为Iliffe向量,则只能获得双重括号.
int **arr2l=calloc(n,sizeof*arr2l);
for (int j=0; j<n; j++)
arr2l[j]=calloc(n,sizeof**arr2l);
arr2[6][6] = arr2l[6][6] = 72;
Run Code Online (Sandbox Code Playgroud)
但随着尺寸的增加,这变得越来越麻烦.
另一个困难是在访问元素之前检查动态数组的边界(这样您就不会触及未正确分配的内存).在真正的阵列可以使用sizeof运营商确定的界限,但这些动态数组携带它们的大小与他们.
如何定义具有快速,连续布局的结构,如数组,但具有一致的语法,用于访问具有索引列表的元素,这些索引对于2D阵列和3D阵列的工作方式相同; 并且所有动态,动态大小可以传递给函数并从函数返回?