您尚未登录。

#1 2013-09-18 16:34:17

依云
会员
所在地: a.k.a. 百合仙子
注册时间: 2011-08-21
帖子: 8,917
个人网站

同一个程序的几种语言版本对照:Haskell, OCaml, Nimrod, Zimbu, Chicken Scheme

此程序用于本社区仓库自动取回仓库服务器,实际使用时带有 set-user-id 标志。其功能完全一样:

编译命令:

# 不开启优化时为 786K
ghc -O2 removepkg

# 默认为速度优化,实际上为大小优化时差异很小
ocamlopt removepkg.ml -o removepkg

# -Os。为速度优化(-O3)时为 211K。不优化时 180K
nimrod c --opt:size removepkg.nim

zimbu --ccarg -O2 removepkg.zu

go build removepkg.go

csc -optimize-level 3 removepkg.scm

strip 之后的程序大小:

  • Haskell: 782K

  • OCaml: 289K

  • Nimrod: 144K

  • Zimbu: 84K

  • Go: 1.2M

  • Chicken (Scheme): 18K

文档情况:

  • Haskell: 列表、按函数名子字符串搜索、按类型模糊搜索(Hoogle)

  • OCaml: 列表、按函数名搜索、按类型搜索(http://search.ocaml.jp/

  • Nimrod: 列表、使用 Google 搜索

附:欢迎提交功能完全一致的其它可编译为二进制程序的语言版本。

最近编辑记录 依云 (2016-01-28 16:56:36)

离线

#2 2013-09-24 19:09:10

GlacJAY
会员
注册时间: 2013-04-28
帖子: 16

Re: 同一个程序的几种语言版本对照:Haskell, OCaml, Nimrod, Zimbu, Chicken Scheme

就是删除指定目录下指定后缀的所有文件?

离线

#3 2013-09-24 21:37:02

依云
会员
所在地: a.k.a. 百合仙子
注册时间: 2011-08-21
帖子: 8,917
个人网站

Re: 同一个程序的几种语言版本对照:Haskell, OCaml, Nimrod, Zimbu, Chicken Scheme

GlacJAY 说:

就是删除指定目录下指定后缀的所有文件?

对。功能够简单吧 ^_^

离线

#4 2013-09-25 17:44:37

haroldwu
会员
所在地: 台中
注册时间: 2013-07-27
帖子: 45
个人网站

Re: 同一个程序的几种语言版本对照:Haskell, OCaml, Nimrod, Zimbu, Chicken Scheme

不知道有沒有理解仙子的原意 >"<
嘗試用 MIT-Scheme 寫了一個,可它的目錄檔案列表讀取功能會把 foo.pkg.tar.xz 的 file type 視爲 xz 而非 pkg.tar.xz
算失敗了
用 Scsh 可能可以
底下嘗試代碼,望能人指教:

(define (distinguish inlist)
  (if (null? inlist)
      (begin (display "finish") (newline))
      (if (equal? (pathname-type (car inlist)) ".pkg.tar.xz")
          (delete-file (->namestring (car inlist)))
          (distinguish (cdr inlist))))) 

(define pkgdir "/tmp/test/")
(distinguish (cddr (directory-read pkgdir)))

最近编辑记录 haroldwu (2013-09-25 17:48:10)


呆丸人
常出沒於 Google+,欢迎互圈~
博客 边陲小岛

离线

#5 2013-09-25 17:59:40

依云
会员
所在地: a.k.a. 百合仙子
注册时间: 2011-08-21
帖子: 8,917
个人网站

Re: 同一个程序的几种语言版本对照:Haskell, OCaml, Nimrod, Zimbu, Chicken Scheme

haroldwu 说:

不知道有沒有理解仙子的原意 >"<
嘗試用 MIT-Scheme 寫了一個,可它的目錄檔案列表讀取功能會把 foo.pkg.tar.xz 的 file type 視爲 xz 而非 pkg.tar.xz
算失敗了
用 Scsh 可能可以
底下嘗試代碼,望能人指教:

(define (distinguish inlist)
  (if (null? inlist)
      (begin (display "finish") (newline))
      (if (equal? (pathname-type (car inlist)) ".pkg.tar.xz")
          (delete-file (->namestring (car inlist)))
          (distinguish (cdr inlist))))) 

(define pkgdir "/tmp/test/")
(distinguish (cddr (directory-read pkgdir)))

大致上是这个意思,不过后缀的判定直接用字符串查找啦。
你这个,有免费的工具可以编译成二进制文件吗?

离线

#6 2013-09-25 19:11:57

haroldwu
会员
所在地: 台中
注册时间: 2013-07-27
帖子: 45
个人网站

Re: 同一个程序的几种语言版本对照:Haskell, OCaml, Nimrod, Zimbu, Chicken Scheme

百合仙子 说:

大致上是这个意思,不过后缀的判定直接用字符串查找啦。
你这个,有免费的工具可以编译成二进制文件吗?

仙子:

理解您的方法了!我本來想用內建的檔案操作函數來弄
直接比對字符串相對容易

剛剛用的工具是 MIT-Scheme 比較「學術」,我換一個 GNU 的開發者們用的 Guile 來寫
(都是 scheme 編譯/解釋器)
程式共五行,編譯結果是成功的,可是不能執行 >"<
只能透過解釋器來跑

這是程式碼

(define pkgdir (opendir "/tmp/test"))
(do ((filename (readdir pkgdir) (readdir pkgdir))) ((eof-object? filename))
  (if (equal? (string-pad filename 11) ".pkg.tar.xz")
      (delete-file filename)))
(closedir pkgdir)

這是執行結果

haroldwu@K40IP:/tmp/test$ guild compile -o utils utils.scm
wrote `utils'

haroldwu@K40IP:/tmp/test$ ls -al
總計 8
drwxr-xr-x  2 haroldwu haroldwu  100  9月 25 19:07 .
drwxrwxrwt 23 root     root     1000  9月 25 18:58 ..
-rw-r--r--  1 haroldwu haroldwu    0  9月 25 19:05 test.pkg.tar.xz
-rw-r--r--  1 haroldwu haroldwu  568  9月 25 19:07 utils
-rw-r--r--  1 haroldwu haroldwu  293  9月 25 18:59 utils.scm

haroldwu@K40IP:/tmp/test$ sudo chmod +x utils

haroldwu@K40IP:/tmp/test$ ./utils
bash: 可執行檔格式錯誤: ./utils

haroldwu@K40IP:/tmp/test$ guile utils.scm 

haroldwu@K40IP:/tmp/test$ ls -al
總計 8
drwxr-xr-x  2 haroldwu haroldwu   80  9月 25 19:08 .
drwxrwxrwt 23 root     root     1000  9月 25 18:58 ..
-rwxr-xr-x  1 haroldwu haroldwu  568  9月 25 19:07 utils
-rw-r--r--  1 haroldwu haroldwu  293  9月 25 18:59 utils.scm

呆丸人
常出沒於 Google+,欢迎互圈~
博客 边陲小岛

离线

#7 2013-09-25 22:24:36

依云
会员
所在地: a.k.a. 百合仙子
注册时间: 2011-08-21
帖子: 8,917
个人网站

Re: 同一个程序的几种语言版本对照:Haskell, OCaml, Nimrod, Zimbu, Chicken Scheme

haroldwu 说:
百合仙子 说:

大致上是这个意思,不过后缀的判定直接用字符串查找啦。
你这个,有免费的工具可以编译成二进制文件吗?

仙子:

理解您的方法了!我本來想用內建的檔案操作函數來弄
直接比對字符串相對容易

剛剛用的工具是 MIT-Scheme 比較「學術」,我換一個 GNU 的開發者們用的 Guile 來寫
(都是 scheme 編譯/解釋器)
程式共五行,編譯結果是成功的,可是不能執行 >"<
只能透過解釋器來跑

這是程式碼

(define pkgdir (opendir "/tmp/test"))
(do ((filename (readdir pkgdir) (readdir pkgdir))) ((eof-object? filename))
  (if (equal? (string-pad filename 11) ".pkg.tar.xz")
      (delete-file filename)))
(closedir pkgdir)

guile 只能把它编译成字节码,而不是机器码。

你这个程序是错误的。这个样子差不多了:

(define pkgdir "/home/lilydjwg/tmpfs/repo")
(define dir (opendir pkgdir))
(do ((filename (readdir dir) (readdir dir))) ((eof-object? filename))
  (if (string-suffix? ".pkg.tar.xz" filename)
    (begin
      (simple-format #t "removing ~A.\n" filename)
      (delete-file (string-append pkgdir "/" filename)))))
(closedir dir)

离线

#8 2013-09-26 00:14:12

haroldwu
会员
所在地: 台中
注册时间: 2013-07-27
帖子: 45
个人网站

Re: 同一个程序的几种语言版本对照:Haskell, OCaml, Nimrod, Zimbu, Chicken Scheme

哇噢懂了
所以 guile 運作起來倒是有點類似 java?
還有個問題
這個工作用 shell script 來做不是更簡潔?


呆丸人
常出沒於 Google+,欢迎互圈~
博客 边陲小岛

离线

#9 2013-09-26 00:18:21

依云
会员
所在地: a.k.a. 百合仙子
注册时间: 2011-08-21
帖子: 8,917
个人网站

Re: 同一个程序的几种语言版本对照:Haskell, OCaml, Nimrod, Zimbu, Chicken Scheme

haroldwu 说:

哇噢懂了
所以 guile 運作起來倒是有點類似 java?
還有個問題
這個工作用 shell script 來做不是更簡潔?

让你们拿编译型语言来啊……

离线

#10 2013-09-26 00:49:34

haroldwu
会员
所在地: 台中
注册时间: 2013-07-27
帖子: 45
个人网站

Re: 同一个程序的几种语言版本对照:Haskell, OCaml, Nimrod, Zimbu, Chicken Scheme

仙子我又來了
這次帶給你 golang

package main

import (
        "fmt"
        "os"
        "strings"
)

func main() {
        pkgdir := "/tmp/test"

        dir, err := os.Open(pkgdir)
        if err != nil {
                return
        }
        defer dir.Close()

        filelist, err := dir.Readdir(-1)
        if err != nil {
                return
        }

        for _, file := range filelist {
                if strings.HasSuffix(file.Name(), ".pkg.tar.xz") {
                        fmt.Println("Removing: " + file.Name())
                        os.Remove(pkgdir + "/" + file.Name())
                }
        }
}

編譯後爲 1.7MB 大小(好大=.=)


呆丸人
常出沒於 Google+,欢迎互圈~
博客 边陲小岛

离线

#11 2013-09-26 10:27:52

依云
会员
所在地: a.k.a. 百合仙子
注册时间: 2011-08-21
帖子: 8,917
个人网站

Re: 同一个程序的几种语言版本对照:Haskell, OCaml, Nimrod, Zimbu, Chicken Scheme

haroldwu 说:

仙子我又來了
這次帶給你 golang

編譯後爲 1.7MB 大小(好大=.=)

静态链接的嘛。strip 之后是 1.2M。

离线

#12 2013-09-26 10:44:08

依云
会员
所在地: a.k.a. 百合仙子
注册时间: 2011-08-21
帖子: 8,917
个人网站

Re: 同一个程序的几种语言版本对照:Haskell, OCaml, Nimrod, Zimbu, Chicken Scheme

haroldwu 说:

仙子我又來了
這次帶給你 golang
)

已添加 :-)

离线

#13 2013-09-26 16:22:42

GlacJAY
会员
注册时间: 2013-04-28
帖子: 16

Re: 同一个程序的几种语言版本对照:Haskell, OCaml, Nimrod, Zimbu, Chicken Scheme

haroldwu 说:

仙子我又來了
這次帶給你 golang
...
編譯後爲 1.7MB 大小(好大=.=)

有选项可以去掉调试信息的,具体忘了。

离线

#14 2013-09-27 01:18:29

haroldwu
会员
所在地: 台中
注册时间: 2013-07-27
帖子: 45
个人网站

Re: 同一个程序的几种语言版本对照:Haskell, OCaml, Nimrod, Zimbu, Chicken Scheme

百合仙子 说:
haroldwu 说:

仙子我又來了
這次帶給你 golang
)

已添加 :-)

仙子好厲害噢,什麼語言都能搞好!


呆丸人
常出沒於 Google+,欢迎互圈~
博客 边陲小岛

离线

#15 2013-09-27 21:24:05

YeLee
BOT
注册时间: 2011-08-19
帖子: 661

Re: 同一个程序的几种语言版本对照:Haskell, OCaml, Nimrod, Zimbu, Chicken Scheme

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <dirent.h>

int procdir(char* dirname, char* extname)
{
    int extlen = strlen(extname);
    DIR* dir = opendir(dirname);
    if (dir) {
        struct dirent* dent = NULL;
        while ((dent = readdir(dir))) {
            int len = strlen(dent->d_name);
            if (dent->d_type == DT_DIR) {
                if ( strcmp(dent->d_name, ".") &&
                            strcmp(dent->d_name, "..") ) {
                    char* subdir = malloc( (strlen(dirname) +
                            strlen(dent->d_name) + 2) * sizeof(char) );
                    strcpy(subdir, dirname);
                    strcat(subdir, "/");
                    strcat(subdir, dent->d_name);
                    procdir(subdir, extname);
                    free(subdir);
                }
            } else if ( (len > extlen) &&
                (!strcmp(extname, dent->d_name + len - extlen)) ) {
                char* filename = malloc( (strlen(dirname) +
                            strlen(dent->d_name) + 2) * sizeof(char) );
                strcpy(filename, dirname);
                strcat(filename, "/");
                strcat(filename, dent->d_name);
                if (remove(filename)) {
                    printf("Can't remove:%s\n", filename);
                } else {
                    printf("Removed:%s\n", filename);
                }
                free(filename);
            }
        }
    }
    closedir(dir);
    return 0;
}

int main(int argc, char* argv[])
{
    if (argc != 3) return -1;
    procdir(argv[1], argv[2]);
    return 0;
}

怎么没有C版的?


小白路过,大家给点面子!

离线

页脚