- android - 多次调用 OnPrimaryClipChangedListener
- android - 无法更新 RecyclerView 中的 TextView 字段
- android.database.CursorIndexOutOfBoundsException : Index 0 requested, 光标大小为 0
- android - 使用 AppCompat 时,我们是否需要明确指定其 UI 组件(Spinner、EditText)颜色
有谁知道 MATLAB 使用哪种算法进行矩阵乘法及其时间复杂度是多少?
最佳答案
为了完整性——如 this thread 中所述, Matlab 使用 DGEMM
(双一般矩阵乘法)例程来自 BLAS (基本线性代数子程序)。
请注意,BLAS 的实现不是单一的——它针对特定的处理器架构进行了调整。因此,如果不查明正在使用哪个版本的 BLAS,您就无法绝对确定您的机器上正在使用哪种算法。
BLAS 的规范指定了每个子程序的输入和输出,并为每个子程序的输出提供了可接受的错误范围。实现可以自由使用他们喜欢的任何算法,只要它们遵循规范即可。
BLAS 的引用实现使用 block matrix multiplication algorithm在 DGEMM
中,将两个 n x n 矩阵相乘的时间复杂度为 O(n^3)。我认为可以合理地假设大多数 BLAS 实现将或多或少地遵循引用实现。
请注意,它不使用朴素的矩阵乘法算法
for i = 1:N
for j = 1:N
for k = 1:N
c(i,j) = c(i,j) + a(i,k) * b(k,j);
end
end
end
这是因为,通常情况下,整个矩阵不会适合 local memory .如果数据不断地移入和移出本地内存,算法就会变慢。 block 矩阵算法将操作分解成小块,这样每个 block 都足够小以适合本地内存,从而减少移入和移出内存的次数。
存在渐进更快的矩阵乘法算法,例如 Strassen algorithm或 Coppersmith-Winograd algorithm它的速度比 O(n^3) 稍快。但是,它们通常不感知缓存并忽略局部性 - 这意味着数据需要不断地在内存中分流,因此对于大多数现代架构而言,整体算法实际上比优化的 block 矩阵乘法算法慢。
维基百科指出,Strassen 算法可以在单核 CPU 上为大于几千的矩阵提供加速,但是加速可能在 10% 左右,BLAS 的开发人员可能认为不值得对于这种罕见的情况(也就是说,1996 年的 this paper 声称对于 n 大约 200 以上的 DGEMM
速度提高了大约 10%——尽管我不知道那是多么的过时)。另一方面,Coppersmith-Winograd 算法“只为现代硬件无法处理的大矩阵提供优势”。
所以答案是 Matlab 使用一种朴素但高效且缓存感知的算法来获得其超快的矩阵乘法。
我通过创建一些视频来更新这个答案,这些视频展示了与朴素算法相比, block 矩阵乘法算法的局部性。
在以下每个视频中,我们都在可视化两个 8x8 矩阵 A 和 B 的乘积以创建乘积 C = <强>A x B。黄色突出显示表示在算法的每个步骤中正在处理每个矩阵 A、B 和 C 中的哪个元素。您可以看到 block 矩阵乘法如何一次仅对矩阵的小块起作用,并多次重复使用这些 block 中的每一个,从而最大限度地减少数据必须移入和移出本地内存的次数.
关于matlab - MATLAB 中的矩阵乘法时间复杂度,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/17716565/
多数元素问题: Given an array of size n, find the majority element. The majority element is the element tha
我有一个简单的问题来找到数组 A 中的第一个唯一元素。但是,令我困扰的是使用不同方法的时间复杂度。到目前为止,我已经尝试过这两种方法。 第一种方法: LinkedHashMap> map = new
STL 中valarray::min 和valarray::max 函数的时间复杂度是多少? 此外,什么是查找各种其他 STL 组件的时间/空间复杂性的良好来源? 最佳答案 O(N) 这些函数不会缓存
我目前正在学习复杂性(或效率,不管你怎么调用它),我在我得到的一本书中读到了它。写了一些我觉得很无意义的东西,我需要一个解释。我试过在线查找,但我没有找到他们给出的这个特定示例的答案。 For an
如何分析算法?是什么让快速排序具有 O(n^2) 的最坏情况性能,而合并排序具有 O(n log(n)) 的最坏情况性能? 最佳答案 这是整个学期的主题。最终,我们讨论的是在算法完成之前必须完成的操作
有谁知道最流行的数据库的 SQL LIKE 运算符的复杂度是多少? 最佳答案 让我们分别考虑三个核心案例。此讨论是特定于 MySQL 的,但也可能适用于其他 DBMS,因为索引通常以类似的方式实现。
Go 编程语言中这个循环的计算复杂度是多少? var a []int for i := 0 ; i doublecap { newcap = cap } else {
我需要创建一个查找函数,其中 (X,Y) 对对应于特定的 Z 值。对此的一个主要要求是我需要尽可能接近 O(1) 复杂度。我的计划是使用 unordered_map。 我通常不使用哈希表进行查找,因为
快速提问,主要满足我对该主题的好奇心。 我正在编写一些带有 SQlite 数据库后端的大型 python 程序,并且将来会处理大量记录,因此我需要尽可能优化。 对于一些功能,我正在通过字典中的键进行搜
Go 编程语言中这个循环的计算复杂度是多少? var a []int for i := 0 ; i doublecap { newcap = cap } else {
我有这个方法: public static int what(String str, char start, char end) { int count=0; for(int i=0;
for (i = 0; i i; j--) //some code that yields O(1) } 我认为上面的代码会产生 n*log(n) 但我看到另一个消息来源说它真的是 n^2
我对 InnoDB 中 OFFSET 的复杂性有疑问。我知道这主要适用于线性复杂性,但如果我在字段上有索引?! 示例: CREATE TABLE `person_rand` ( `p_id` int
我嵌套了一些 if/else 语句,但我想减少它们的开销。 在示例中,我正在评估从哪个下拉列表中单击了 li 项目,以及该 li 项目是否是第一个 (currentIndex === 0)。 代码:
这是我的第一个问题,所以我希望我没有违反任何规则。我终于设法为基数排序算法编写代码,但我想知道我是否做错了。让我觉得我的算法看起来复杂度为 O(n^3),但众所周知,基数排序是一个 O(k.n) 算法
几周前我认识了 big-O 并试图掌握它,但是尽管有很多关于计算时间复杂度的 Material ,但我似乎无法找到如何使算法更高效。 我一直在练习 Codility 中的演示挑战: Write a f
在最近的一次考试中,我们得到了一个函数来计算在未排序的 ArrayList 中出现了多少个 double (不是原始 double,而是一个项目出现两次的次数)。 我正确地确定了 Big O 复杂度为
以下循环的大 O 复杂度是多少: for each vertex u ∈ C do for each vertex v ∈ C and v > u do 我在这里做的是想象以下集合 {
我想对条款进行排序,使每个条款都是下一个条款的大 O √n√logn √n log( n^30) n/〖(logn)〗^2 〖16〗^(log√n) 谁能帮忙找到顺序? 最佳答案 claim :16
我正在尝试计算此选择排序实现的大 O 时间复杂度: void selectionsort(int a[], int n) { int i, j, mini
我是一名优秀的程序员,十分优秀!