本文介绍了哈斯克尔repa - 如何降低阵列和收益指数?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在GNU八度这个code -

In GNU Octave this code -

[e, ix] = min(X);

将返回最小元素,它的位置。 如何你这repa任意二元函数?

这是我想出了:

min x = z $ foldl' f (e,0,0) es
  where
    (e:es) = toList x
    f (a,ix,r) b = let ix' = ix+1 in if a < b then (a,ix',r) else (b,ix',ix')
    z (a,ix,r) = (a,r)

在上面的例子中,我们转换repa 1D矩阵列出和使用与foldl'(从Data.List模块)与两个累加器 - 一个用于计数迭代(ⅸ)等保存分钟元件(R)的位置。但是,使用repa的整点是使用数组,而不是名单!

In above example we convert repa 1D matrix to list and use foldl' (from Data.List) with two accumulators - one for counting iterations (ix) and other to save position of min element (r). But the whole point of using repa is to use arrays, not lists!

在repa有数组类型(褶皱和foldP)二倍 - 但他们只能采取类型的功能(A - > A - > A) - 意思,我能不能通过元组蓄电池它。还有遍历,它可以在原则上,减少维数组为标量数组:

In repa there are two folds for Array type (foldS and foldP) - but they can only take function of type (a -> a -> a) - meaning, I cannot pass tuple with accumulators to it. There is also traverse, which can, in principle, reduce 1D array to a scalar array:

min x = traverse x to0D min
  where
    to0D (Z:.i) = Z
    min f (Z) = ??? -- how to get elements for comparison?

,想到的第一件事是

The first thing that comes to mind is

[f (Z:.i) | i <- [1..n]], where n = (\(Z:.i) -> i) $ extent x

但是,这也将转换成数组列表,而不是在阵列上做计算。

But this will also convert array to list, instead of doing computation on the array.

推荐答案

我在Repa的专家,但这似乎一维数组。大概可以适用于其他方面。

I'm no expert on Repa, but this seems to work for 1-D arrays. It can probably be adapted for other dimensions.

import Data.Array.Repa

indexed arr = traverse arr id (\src idx@(Z :. i) -> (src idx, i))

minimize arr = foldP f h t
  where
    (Z :. n) = extent arr
    arr' = indexed arr
    h = arr' ! (Z :. 0)
    t = extract (Z :. 1) (Z :. (n-1)) arr'
    f min@(valMin, iMin) x@(val, i) | val < valMin = x
                                    | otherwise = min

这篇关于哈斯克尔repa - 如何降低阵列和收益指数?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

10-10 20:32