2011年12月12日月曜日

wsgiref を使ってpythonで書いた HTTPサーバで画像をアップロード


結構大変だったのでメモ。参考文献は忘れたのでパス。
HTTPでアクセスできるサーバを、 wsgiref というモジュールで書きました。

以下のプログラムどっかでを実行して、
http://localhost:8080 にブラウザからアクセスすると、フォームが現れます。
ブラウザから画像を選択 -> サーバがカレントディレクトリに aaa.png という名前で保存します。

import cgi, StringIO
from wsgiref import simple_server
import numpy, Image

class Selector(object):
    def __init__(self, table, notfound = None):
        tmp = sorted(table, key=lambda x:len(x), reverse=True)
        table = [(x, table[x]) for x in tmp]
        self.table = table # url table
        if notfound:
            self.notfound = notfound # when not found

    def __call__(self, environ, start_response):
        name = "SCRIPT_NAME"
        info = "PATH_INFO"

        scriptname = environ.get(name, "")
        pathinfo = environ.get(info, "")

        for p, app in self.table:
            print p, pathinfo
            if p == "" or p =="/" or pathinfo.startswith(p):
                print app
                return app(environ, start_response)

        if pathinfo == p or pathinfo.startswith(p) and pathinfo[len(p)] == "/":
            scriptname = scriptname + p
            pathinfo = pathinfo[len(p):]
            environ[name] = scriptname
            environ[info] = pathinfo
            return app(environ, start_response)

        return self.notfound(environ, start_response)

    def notfound(self, environ, start_response):
        start_response('404 Not Found', [('Content-type', 'text/html')])
        fp = StringIO.StringIO()
        fp.write(r"""<html><header><title>Not Found</title></header>
<body> 
<H1> URL not found. </H1>
<ul>
""")
        for entry in self.table:
            fp.write(r"<li/> %s %s" % (entry[0], entry[1]))
        fp.write(r"</ul></body></html>")
        fp.seek(0)
        
        return fp

def imageupload(environ, start_response):
    try:
        clen = int(environ["CONTENT_LENGTH"])
    except:
        clen = 0

    f = cgi.FieldStorage(fp=environ["wsgi.input"], 
                         environ=environ, 
                         keep_blank_values=True)
    handle = open("aaa.png", "wb")
    handle.write(f["filename"].file.read())
    handle.close()


    fp = StringIO.StringIO()
    fp.write(r"<html><body> environmental variables <dl>")

    for key in sorted(environ.keys()):
        fp.write(r"<dt>%s</dt><dd>%s</dd>" % (key, environ[key]))
    fp.write(r"</dl></body></html>")
    fp.seek(0)
    
    start_response("200 OK", [("Content-type", "text/html")])
    return fp

def showtop(environ, start_response):
    start_response("200 OK", [("Content-type", "text/html")])
    return r"""<html><body> 
imageupload 
<form action="/image" enctype="multipart/form-data" method="post">
<input type="file" name="filename"><input type="submit" value="Upload">
</form>
</body></html>"""

if __name__ == '__main__':
    application = Selector({"/":showtop, "/image":imageupload})
    srv = simple_server.make_server('', 8080, application)
    srv.serve_forever()

2011年12月8日木曜日

python の site-packagesとdist-packages


Python のインストールパスは、バージョンごと、モジュールごとで異なる。

Python 2.5 以前
  • public モジュール を python-support でインストール (apt-get)
    /usr/lib/python2.X/site-packages
  • public モジュールを ローカルでインストール (easy_install)
    /usr/local/lib/python2.X/site-packages
  • 独自モジュールをローカルでインストール
    /usr/local/lib/python2.X/site-packages
Python 2.6, 2.7
  • public モジュール を python-support でインストール (apt-get)
    /usr/lib/python2.X/dist-packages
  • public モジュールを ローカルでインストール (easy_install)
    /usr/local/lib/python2.X/dist-packages
  • 独自モジュールをローカルでインストール
    /usr/local/lib/python2.X/site-packages

Python 3
  • public モジュール を python-support でインストール (apt-get)
    /usr/lib/python3/dist-packages
  • public モジュールを ローカルでインストール (easy_install)
    /usr/lib/python3/dist-packages
  • 独自モジュールをローカルでインストール
    /usr/local/lib/python3/site-packages



参考
http://www.debian.org/doc/packaging-manuals/python-policy/ch-python.html

2011年12月6日火曜日

/usr/include/gnu/stubs.h:7:27: error: gnu/stubs-32.h: No such file or directory


HTK 3.4.1 を 64bit の Ubuntu 10.04 でコンパイルしようとすると、

/usr/include/gnu/stubs.h:7:27: error: gnu/stubs-32.h: No such file or directory

というエラーが出る。

そんなときは:

sudo apt-get install g++-multilib


Reference:

2011年12月5日月曜日

boost::python::numeric::array に 値を渡す。 (embedded python)

Boost python に vector を簡単に渡したいときは、次のようにする。

#include <boost/python.hpp>
#include <boost/python/numeric.hpp>
#include <boost/python/suite/indexing/vector_indexing_suite.hpp>
#include <iostream>
#include <vector>

namespace bp = boost::python;

int main()
{
  Py_Initialize();

  bp::object main = bp::import("__main__");
  bp::object namesp = main.attr("__dict__");
  bp::numeric::array::set_module_and_type("numpy", "ndarray");
  // use numpy.ndarray as numeric::array

  bp::class_<std::vector<int> > ("PyVecInt")
    .def(bp::vector_indexing_suite<std::vector<int> > () );
  // tell python how to access the vector

  std::vector<int> vec;
  for(int i=0; i<20; i++)
    vec.push_back(i);

  bp::numeric::array ary(vec); // vector -> ndarray
  ary.resize(bp::make_tuple(4, 5));

  namesp["pyary"] = ary;  // c++ binary --> python interpreter
  exec("print pyary", namesp);
  exec("print pyary.shape", namesp);
  exec("print type(pyary)", namesp);
}


すると、次のような結果が得られる.

[[  0   1   4   9  16]
 [ 25  36  49  64  81]
 [100 121 144 169 196]
 [225 256 289 324 361]]
(4, 5)
<type 'numpy.ndarray'>


等価な python code
#equivalent python code
import numpy
pyary = numpy.array(range(20))
pyary.resize(4, 5)
print pyary
print pyary.shape
print type(pyary)

2011年12月2日金曜日

BibTex: How to change the reference style


Assumption: 
You use cite.sty to allow the multiple references for \cite. 
\usepackage{cite}
e.g., \cite{Yukawa1900-Nature, Tomonaga1901-Nature}


When you compile the line above, you will see
[1, 2] or [Yukawa 1900, Tomonaga 1900], for instance.


If you want to change them into, e.g., (Yukawa 1900; Tomonaga 1901), 

insert the following three lines in the preamble:
\renewcommand\citeleft{(}
\renewcommand\citeright{)}
\renewcommand\citepunct{;}

Reference
The bottom of cite.sty
http://ftp.yz.yamagata-u.ac.jp/pub/CTAN/macros/latex/contrib/cite/cite.sty

bibtex の 引用形式を調整したい。

前提
\usepackage{cite}
で、\cite コマンドに複数の入力を許可している。
e.g., \cite{Yukawa1900-Nature, Tomonaga1901-Nature}

この状態で普通にコンパイルすると、 [1, 2] とかになる。
あるいは、 [Yukawa 1900, Tomonaga 1901]
のようになる。

ここで、 \begin{document} の前に

\renewcommand\citeleft{(}
\renewcommand\citeright{)}
\renewcommand\citepunct{;}

を入れると、
(Yukawa 1900; Tomonaga 1901)
になる。



参考文献
cite.sty の最後のほう
http://ftp.yz.yamagata-u.ac.jp/pub/CTAN/macros/latex/contrib/cite/cite.sty