Subscribed unsubscribe Subscribe Subscribe

k-yamadaのブログ

プログラミングのメモ

UTF-8からShift_JISに変換する時の注意

(http://qiita.com/akkun_choi/items/a1fbde5d6d065df3fc97)」を参考にやってみたのですが、うまくencode出来なかったので、一部修正しました。

以下はMac OS XUbuntuで動作確認しています。

ソースコード

# app/models/encode_utils.rb: 

class EncodeUtils
  class << self
    def to_sjis(str)
      sjis_safe(str).encode("Shift_JIS",
        :invalid => :replace, :undef => :replace)
    end

    def sjis_safe(str)
      [
        ["FF5E", "301C"], # wave-dash
        ["FF0D", "2212"], # full-width minus
        ["FFE0", "00A2"], # cent as currency
        ["FFE1", "00A3"], # lb(pound) as currency
        ["FFE2", "00AC"], # not in boolean algebra
        ["2015", "2014"], # hyphen
        ["2225", "2016"], # double vertical lines
      ].inject(str) do |s, (before, after)|
        before_str = before.to_i(16).chr('UTF-8')
        after_str  = after.to_i(16).chr('UTF-8')
        s.gsub(before_str, after_str)
      end
    end
  end
end

rspec

# spec/models/encode_utils_spec.rb:

# -*- coding: utf-8 -*-
require 'spec_helper'

describe EncodeUtils do
  def hex_to_sjis(hex)
    hex.to_i(16).chr('UTF-8').encode("Shift_JIS")
  end

  describe '.to_sjis' do
    it 'hiragana should change to sjis' do
      expect(EncodeUtils.to_sjis("あいうえお")).to eq("あいうえお".encode("Shift_JIS"))
    end

    it 'harf-width special char should change to sjis' do
      expect(EncodeUtils.to_sjis("〜−¢£¬−‖")).to eq("〜−¢£¬−‖".encode("Shift_JIS"))
    end

    it 'wave-dash should change to sjis' do
      expect(EncodeUtils.to_sjis("")).to eq(hex_to_sjis("301C"))
    end

    it 'full-width minus should change to sjis' do
      expect(EncodeUtils.to_sjis("")).to eq(hex_to_sjis("2212"))
    end

    it 'cent as currency should change to sjis' do
      expect(EncodeUtils.to_sjis("")).to eq(hex_to_sjis("00A2"))
    end

    it 'lb(pound) as currency should change to sjis' do
      expect(EncodeUtils.to_sjis("")).to eq(hex_to_sjis("00A3"))
    end

    it 'not in boolean algebra should change to sjis' do
      expect(EncodeUtils.to_sjis("")).to eq(hex_to_sjis("00AC"))
    end

    it 'hyphen should change to sjis' do
      expect(EncodeUtils.to_sjis("")).to eq(hex_to_sjis("2014"))
    end

    it 'double vertical lines should change to sjis' do
      expect(EncodeUtils.to_sjis("")).to eq(hex_to_sjis("2016"))
    end
  end
end

backbone.jsとWebWorkerを共存させた時に、backbone.jsでアンカー変更イベントが発生しない

Backbone.js version: 0.5.3

事象

MVCフレームワークとしてbackbone.jsを使用し、ページ内でWebWorkerのスレッドを起動すると、backbone.jsのアンカー(#xxx)変更イベントが発生しなくなる

暫定処置

以下のようにコードを修正すると、正常に動作するようになります。

// backbone.js  Line 796~

//$(window).bind('hashchange', this.checkUrl); 
var self = this;
window.onhashchange = function () {
   self.checkUrl();
}

javascriptでhashのキーを変数で指定する

hashのキーに変数を指定しようとしても、ハッシュのkeyとして指定された値は変数展開されません。
以下の例では、"key"という文字列がhashのkeyになります。

var key = "hoge";
var h = {key : "fuga"};
console.log(h) // => Object {key: "fuga"}


hashのkeyに変数を指定したい場合は、以下のような関数を作ると便利です。

function hash(key, value) {
  var h = {};
  h[key] = value;
  return h;
}

var key = "hoge";
var h = hash(key, "fuga");
console.log(h) => Object {hoge: "fuga"}

nginxをwebsocketのリバースプロキシサーバにするときのExample

https://github.com/yaoweibin/nginx_tcp_proxy_module/wiki/websocket

jrubyでdaemon化する

Ruby daemons and JRuby - alternative options
http://stackoverflow.com/questions/5349629/ruby-daemons-and-jruby-alternative-options

上記の質問サイトで紹介されていたのですが、jrubyでも使えるdaemonライブラリがありました。
https://github.com/colinsurprenant/raad

SISPの進捗メモ

読書開始日

2012/11/23

進め方

問題はgauche(Schemeの方言)で解答する
問題は自力で解く。わからなかったら答え(http://community.schemewiki.org/?SICP-Solutions)をみて赤字で正答を書く。

Q1.1

gosh> 10
10
gosh> (+ 5 3 4)
12
gosh> (- 9 1)
8
gosh> (/ 6 2)
3
gosh> (+ (* 2 4) (- 4 6))
6
gosh> (define a 3)
a
gosh> (define b (+ a 1))
b
gosh> (+ a b (* a b))
19
gosh> (= a b)
#f
gosh> 
(if (and (> b a) (< b (* a b)))
    b
    a)
=>4
gosh> 
(cond ((= a 4) 6 )
         ((= b 4) (+ 6 7 a))
         (else 25))
=>16
gosh> (+ 2 (if (> b a) b a))
=>6
gosh> 
(* (cond ((> a b) a)
             ((< a b) b)
            (else -1))
    (+ a 1))
16

Q1.2

gosh> 
(/ (+ 5 
        4 
        (- 2
            (- 3
                (+ 6
                    (/ 4 5)))))
    (* 3
       (- 6 2)
       (- 2 7)))
=> 37/150

Q1.3

2012/11/25
3つの数を引数としてとり、大きい2つの数の2乗の和を返す手続き

(define (square x)
  (* x x))

(define (sum-of-squares x y)
  (+ (square x) (square y)))

(define (sum-of-squares-of-larger-2 x y z)
  (define larger-2 (cdr (sort (list x y z))))
  (sum-of-squares (car larger-2) (car (cdr larger-2)))

(sum-of-squares-of-larger-2 5 4 3)
=> 41

Q1.4

gosh> 
(define (a-plus-abs-b a b)
  ((if (> b 0) + -) a b))  
a-plus-abs-b
gosh> (a-plus-abs-b 10 5)
15
gosh> (a-plus-abs-b 10 -5)
15

Q1.5

(define (p) (p))

(define (test x y)
  (if (= x 0)
  0
  y))

(test 0 (p))

goshで実行した結果フリーズした。
・作用的順序で評価する場合の振る舞い
手続きpの評価が無限ループする?
Using applicative-order evaluation, the evaluation of (test 0 (p)) never terminates, because (p) is infinitely expanded to itself:

・正規順序で評価する場合の振る舞い
0が返る?
Using normal-order evaluation, the expression evaluates, step by step, to 0:
(test 0 (p))
(if (= 0 0) 0 (p))
(if #t 0 (p))
0


Macにgaucheの開発環境を作った

Gaucheインストール

現時点での最新バージョン(0.9.3.3)をソースからインストールします。
最新バージョンは公式サイト( http://practical-scheme.net/gauche/download-j.html )で確認して下さい

$ cd ~/src
$ wget http://prdownloads.sourceforge.net/gauche/Gauche-0.9.3.3.tgz
$ gzcat Gauche-0.9.3.3.tgz | tar xf -
$ cd Gauche-0.9.3.3
$ ./configure
$ make
$ sudo make install
$ gosh
gosh> (exit)
$

Emacsインストール

私は普段vimを使っていますが、Gaucheの書籍でオススメされてるので、Gaucheのコード書くときはEmacsを使うことにします。
Mac用のバイナリを以下のサイトからダウンロードしてインストールしてください。
http://emacsformacosx.com/

Emacsのセットアップ

参考:http://karetta.jp/book-node/gauche-hacks/004682
~/.emacsファイルを作成し、以下を入力します

;; Gaucheのデフォルトエンコーディングに合わせます。
;; Gaucheのデフォルトエンコーディングがeuc-jpの時はutf-8をeuc-jpに
;; してください。
(setq process-coding-system-alist
      (cons '("gosh" utf-8 . utf-8) process-coding-system-alist))
;; goshインタプリタのパスに合わせます。-iは対話モードを意味します。
(setq gosh-program-name "/usr/local/bin/gosh -i")
;; schemeモードとrun-schemeモードにcmuscheme.elを使用します。
(autoload 'scheme-mode "cmuscheme" "Major mode for Scheme." t)
(autoload 'run-scheme "cmuscheme" "Run an inferior Scheme process." t)
;; ウィンドウを2つに分け、一方でgoshインタプリタを実行するコマンドを定義します。
(defun scheme-other-window ()
  "Run scheme on other window"
  (interactive)
  (switch-to-buffer-other-window
   (get-buffer-create "*scheme*"))
  (run-scheme gosh-program-name))
;; そのコマンドをCtrl-csで呼び出します。
(define-key global-map
  "\C-cs" 'scheme-other-window)

;; 直前/直後の括弧に対応する括弧を光らせます。
(show-paren-mode)

;; 以下はインデントの定義です。
(put 'and-let* 'scheme-indent-function 1)
(put 'begin0 'scheme-indent-function 0)
(put 'call-with-client-socket 'scheme-indent-function 1)
(put 'call-with-input-conversion 'scheme-indent-function 1)
(put 'call-with-input-file 'scheme-indent-function 1)
(put 'call-with-input-process 'scheme-indent-function 1)
(put 'call-with-input-string 'scheme-indent-function 1)
(put 'call-with-iterator 'scheme-indent-function 1)
(put 'call-with-output-conversion 'scheme-indent-function 1)
(put 'call-with-output-file 'scheme-indent-function 1)
(put 'call-with-output-string 'scheme-indent-function 0)
(put 'call-with-temporary-file 'scheme-indent-function 1)
(put 'call-with-values 'scheme-indent-function 1)
(put 'dolist 'scheme-indent-function 1)
(put 'dotimes 'scheme-indent-function 1)
(put 'if-match 'scheme-indent-function 2)
(put 'let*-values 'scheme-indent-function 1)
(put 'let-args 'scheme-indent-function 2)
(put 'let-keywords* 'scheme-indent-function 2)
(put 'let-match 'scheme-indent-function 2)
(put 'let-optionals* 'scheme-indent-function 2)
(put 'let-syntax 'scheme-indent-function 1)
(put 'let-values 'scheme-indent-function 1)
(put 'let/cc 'scheme-indent-function 1)
(put 'let1 'scheme-indent-function 2)
(put 'letrec-syntax 'scheme-indent-function 1)
(put 'make 'scheme-indent-function 1)
(put 'multiple-value-bind 'scheme-indent-function 2)
(put 'match 'scheme-indent-function 1)
(put 'parameterize 'scheme-indent-function 1)
(put 'parse-options 'scheme-indent-function 1)
(put 'receive 'scheme-indent-function 2)
(put 'rxmatch-case 'scheme-indent-function 1)
(put 'rxmatch-cond 'scheme-indent-function 0)
(put 'rxmatch-if  'scheme-indent-function 2)
(put 'rxmatch-let 'scheme-indent-function 2)
(put 'syntax-rules 'scheme-indent-function 1)
(put 'unless 'scheme-indent-function 1)
(put 'until 'scheme-indent-function 1)
(put 'when 'scheme-indent-function 1)
(put 'while 'scheme-indent-function 1)
(put 'with-builder 'scheme-indent-function 1)
(put 'with-error-handler 'scheme-indent-function 0)
(put 'with-error-to-port 'scheme-indent-function 1)
(put 'with-input-conversion 'scheme-indent-function 1)
(put 'with-input-from-port 'scheme-indent-function 1)
(put 'with-input-from-process 'scheme-indent-function 1)
(put 'with-input-from-string 'scheme-indent-function 1)
(put 'with-iterator 'scheme-indent-function 1)
(put 'with-module 'scheme-indent-function 1)
(put 'with-output-conversion 'scheme-indent-function 1)
(put 'with-output-to-port 'scheme-indent-function 1)
(put 'with-output-to-process 'scheme-indent-function 1)
(put 'with-output-to-string 'scheme-indent-function 1)
(put 'with-port-locking 'scheme-indent-function 1)
(put 'with-string-io 'scheme-indent-function 1)
(put 'with-time-counter 'scheme-indent-function 1)
(put 'with-signal-handlers 'scheme-indent-function 1)
(put 'with-locking-mutex 'scheme-indent-function 1)
(put 'guard 'scheme-indent-function 1)