裏 RjpWiki

文字通り,RjpWiki の裏を行きます
R プログラム コンピュータ・サイエンス 統計学

ダメ出し:アトキンの篩

2012年02月13日 | ブログラミング

2011-05-11 R でエラトステネスの篩 の後半に,アトキンの篩のプログラムが掲載されている。

ご本人も「多分条件判定減らすとかしてRに合った実装しないとダメなんだと思う」というとおり,ベクトル化をはかる。ちなみに,元のプログラムでは for を避けるためか while で書いているがこれはほとんど意味がない。

limit = 10000000 で 23 秒かかっていたものが,書き直すと 0.4 秒ほどで計算終了ということになった。

プログラムは以下の通り。

atkin <- function(limit = 1e+06, return = FALSE) {
    sqrt.limit <- sqrt(limit)
    isprime <- logical(limit)
    for (z in c(1, 5)) {
        for (y in seq.int(z, sqrt.limit, by = 6)) {
            y2 <- y * y
            max.x <- floor(sqrt((limit - y2) / 4))
            if (1 <= max.x) {
                n <- 4 * (1:max.x) ^ 2 + y2
                isprime[n] <- !isprime[n]
            }
            x <- y + 1
            max.x <- floor(sqrt((limit + y2) / 3))
            if (x <= max.x) {
                n <- 3 * seq.int(x, max.x, by = 2) ^ 2 - y2
                isprime[n] <- !isprime[n]
            }
        }
    }
    for (z in c(2, 4)) {
        for (y in seq.int(z, sqrt.limit, by = 6)) {
            y2 <- y * y
            max.x <- floor(sqrt((limit - y2) / 3))
            if (1 <= max.x) {
                n <- 3 * seq.int(1, max.x, by = 2) ^ 2 + y2
                isprime[n] <- !isprime[n]
            }
            x <- y + 1
            max.x <- floor(sqrt((limit + y2) / 3))
            if (x <= max.x) {
                n <- 3 * seq.int(x, max.x, by = 2) ^ 2 - y2
                isprime[n] <- !isprime[n]
            }
        }
    }
    for (y in seq.int(3, sqrt.limit, by = 6)) {
        y2 <- y * y
        for (x in 1:2) {
            max.x <- floor(sqrt((limit - y2) / 4))
            if (x <= max.x) {
                n <- 4 * seq.int(x, max.x, by = 3) ^ 2 + y2
                isprime[n] <- !isprime[n]
            }
        }
    }
    for (n in seq.int(5, sqrt.limit, by = 2)) {
        if (isprime[n]) {
            isprime[1:(limit %/% (n * n)) * n * n] <- FALSE
        }
    }
    isprime[2] <- isprime[3] <- TRUE
    if (return) {
        which(isprime)
    }
}

コメント   この記事についてブログを書く
« ダメ出し:R で円周率計算(2) | トップ | そんなものじゃないだろう »
最近の画像もっと見る

コメントを投稿

ブログ作成者から承認されるまでコメントは反映されません。

ブログラミング」カテゴリの最新記事