2007/11/22

Javascript 간이 closure

a=[10,3,7,12,1,43]
10,3,7,12,1,43
a.sort()
1,10,12,3,43,7
[10, 3, 7, 12, 1, 43].sort()
1,10,12,3,43,7
------------------------
Array.prototype.map=function(f) { var result=[]; for (i in this) result[i]=f(this[i]); return result; }
function (f) { var result = []; for (i in this) { result[i] = f(this[i]); } return result; }
[1,2,3,4,5].map(function(x) { return x*x })
1,4,9,16,25
[10, 3, 7, 12, 1, 43].sort().map(function(x) {return x*x })
1,100,144,9,1849,49
[10, 3, 7, 12, 1, 43].sort().map(function(x) {return x*x }).sort()
1,100,144,1849,49,9

인자가 n개일땐 어떨지 모르겠다.

Javascript 연습 - 배열은 객체다?/Prototype을 통한 Native 확장

파란색 글자를 따라가면서 한줄한줄 쳐봅시다.
줄바꿈은 Shift+Enter 사용하면 됩니다.
Javascript Shell 이쪽에서 IE/FF 골라봅니다. FF 추천!
  • // function 이해
a=' fccc sad fwe '
fccc sad fwe
괄호만들기=function(x){return '('+x+')'}
function (x) { return "(" + x + ")"; }
괄호만들기(a)
( fccc sad fwe )
제품['상품명']=' 야매너구리 '
ReferenceError on line 1: \uC81C\uD488 is not defined
제품=[]
제품['상품명']=' 야매 너구리 '
야매 너구리
제품['포장']=function() { return '('+this['상품명']+')' }
function () { return "(" + this.\uC0C1\uD488\uBA85 + ")"; }
제품.포장
function () { return "(" + this.\uC0C1\uD488\uBA85 + ")"; }
제품.포장()
( 야매 너구리 )

  • // Trim 만들고 Prototype 에 확장
' 야메 너구리 '.replace(/^\s*|\s*$/g,'')
야메 너구리
'@@'+' 야메 너구리 '.replace(/^\s*|\s*$/g,'')+'@@'
@@야메 너구리@@
String.trim=function() {return this.replace(/^\s*|\s*$/g,'')}
function () { return this.replace(/^\s*|\s*$/g, ""); }
a=' 야메 '
야메
a.trim()
TypeError on line 1: a.trim is not a function
String.prototype.trim=function() {return this.replace(/^\s*|\s*$/g,'')}
function () { return this.replace(/^\s*|\s*$/g, ""); }
a.trim()
야메
'@@'+a.trim()+'@@'
@@야메@@
'@@'+' 야매 '.trim()+'@@'
@@야매@@
  • for x in z 를 이용한 심화 예제, type 알아보기
// 배열에 있는 값들을 합치는 method를 만들어봅니다.
Array.prototype.sum=function() { for (x in this) result+=x; return result; }
function () { for (x in this) { result += x; } return result; }
a=[1,2,3,4,5,6]
1,2,3,4,5,6
a.sum()
ReferenceError on line 2: reference to undefined property "result"
// 아무리 타입캐스팅이 관대하지만 좀 너무 했습니다. 초기화 정도는 해줍시다.
Array.prototype.concats=function() { var result=''; for (x in this) result+=x; return result; }
function () { var result = ""; for (x in this) { result += x; } return result; }
a.concats()
012345sumconcats
// 오류를 발견했습니다. 첫째로는 값을 가져와야하는데 키를 가져왔고 method 명까지 같이 나와버렸습니다.
props(a)
Fields: 0, 1, 2, 3, 4, 5
Methods of prototype: concats, sum
// Shell 내장함수인 props 는 필드와 Method 를 구분합니다. 어떻게 할까요?
props
function props(e, onePerLine) { if (e === null) { println("props called with null argument", "error"); return; } if (e === undefined) { println("props called with undefined argument", "error"); return; } var ns = ["Methods", "Fields", "Unreachables"]; var as = [[], [], []]; var p, j, i; var protoLevels = 0; for (p = e; p; p = p.__proto__) { for (i = 0; i < protolevel =" -1;" p =" e;" p =" p.__proto__)" protolevel =" 0;" type =" 1;" style="color: rgb(255, 0, 0);">typeof e[a] == "function") { type = 0; } } catch (er) { type = 2; } as[type][protoLevel].push(a); } function times(s, n) { return n ? s + times(s, n - 1) : ""; } for (j = 0; j < i =" 0;">
// 호오 typeof e[a] == "function" 이 부분이 눈에 들어오는군요
a
1,2,3,4,5,6
props(a)
Fields: 0, 1, 2, 3, 4, 5
Methods of prototype: concats, sum
typeof a['concats']
function
typeof a['0']
number
Array.prototype.concats=function() { var result=''; for (x in this) result+= typeof this[x]=='function' ? '' : this[x]; return result; }
function () { var result = ""; for (x in this) { result += typeof this[x] == "function" ? "" : this[x]; } return result; }
a.concats()
123456
a
1,2,3,4,5,6
a=['이','사','육','팔','십']
이,사,육,팔,십
a.concats()
이사육팔십


수고하셨습니다 :)

2007/10/05

Oracle10g - Xmlagg를 사용한 가로 Group by Query

C군의 질문

A | B
------
A | 가
B | 가
C | 가
a | 나
B | 나
C | 다

일때

가 | ABC
나 | aB
다 | C

를 뽑아낼 수 없을까?

라고 하여 요렇게 조렇게 실험해봤음.
일종의 String Aggregation 인데 http://www.oracle-base.com/articles/10g/StringAggregationTechniques.php 이런 방법도 있지만 왠지 복잡하고 10g 기능을 사용하고 싶어서 뒤져보기 시작.

(10g 가 아니라면 sys_connect_by_path 를 사용하는 방법이 무난. 비용이 좀 든다는 단점이 있다고 한다.)
SELECT deptno,
LTRIM(MAX(SYS_CONNECT_BY_PATH(ename,','))
KEEP (DENSE_RANK LAST ORDER BY curr),',') AS employees
FROM (SELECT deptno,
ename,
ROW_NUMBER() OVER (PARTITION BY deptno ORDER BY ename) AS curr,
ROW_NUMBER() OVER (PARTITION BY deptno ORDER BY ename) -1 AS prev
FROM emp)
GROUP BY deptno
CONNECT BY prev = PRIOR curr AND deptno = PRIOR deptno
START WITH curr = 1;

DEPTNO EMPLOYEES
---------- --------------------------------------------------
10 CLARK,KING,MILLER
20 ADAMS,FORD,JONES,SCOTT,SMITH
30 ALLEN,BLAKE,JAMES,MARTIN,TURNER,WARD


XMLAGG 로 GROUP BY를 할 수 있다는 사실을 발견

SELECT B, XMLAGG(A) FROM (
SELECT 'A' A, '가' B FROM DUAL UNION ALL
SELECT 'B' , '가' FROM DUAL UNION ALL
SELECT 'C' , '가' FROM DUAL UNION ALL
SELECT 'a' , '나' FROM DUAL UNION ALL
SELECT 'B' , '나' FROM DUAL UNION ALL
SELECT 'C' , '다' FROM DUAL)
GROUP BY B

하지만 이렇게 하면 오류가 난다.
타입이 맞지 않기 때문이다. 인자를 XML형으로 바꾸기 위해 XMLELEMENT를 사용한다.
컬럼에 C라는 Tag 명을 붙여서 보자.

SELECT B, XMLAGG(XMLELEMENT(C,A)) A FROM (
SELECT 'A' A, '가' B FROM DUAL UNION ALL
SELECT 'B' , '가' FROM DUAL UNION ALL
SELECT 'C' , '가' FROM DUAL UNION ALL
SELECT 'a' , '나' FROM DUAL UNION ALL
SELECT 'B' , '나' FROM DUAL UNION ALL
SELECT 'C' , '다' FROM DUAL)
GROUP BY B

결과는 나오지만 충분하지 않다. 실제로 Application 에서 사용하려면 XML 타입이라 맞지 않기 때문이다.
GETSTRINGVAL()을 붙여서 형변환을 해준다.

SELECT B, XMLAGG(XMLELEMENT(C,A)).GETSTRINGVAL() A
FROM (
SELECT 'A' A, '가' B FROM DUAL UNION ALL
SELECT 'B' , '가' FROM DUAL UNION ALL
SELECT 'C' , '가' FROM DUAL UNION ALL
SELECT 'a' , '나' FROM DUAL UNION ALL
SELECT 'B' , '나' FROM DUAL UNION ALL
SELECT 'C' , '다' FROM DUAL)
GROUP BY B

B | A
가 | ABC
나 | aB
다 | C

원하는 결과가 나왔다.
Tag 을 제거하자 기왕 xml도 건든 김에 정규표현식으로 제거해보자.


SELECT B, REGEXP_REPLACE(XMLAGG(XMLELEMENT(C,A)).GETSTRINGVAL(), '<[C/]+>', '') A
FROM (
SELECT 'A' A, '가' B FROM DUAL UNION ALL
SELECT 'B' , '가' FROM DUAL UNION ALL
SELECT 'C' , '가' FROM DUAL UNION ALL
SELECT 'a' , '나' FROM DUAL UNION ALL
SELECT 'B' , '나' FROM DUAL UNION ALL
SELECT 'C' , '다' FROM DUAL)
GROUP BY B

B | A
------
가 | ABC
나 | aB
다 | C

게임오버 :)

2007/08/08

NetBeans IDE 6.0 M10 에서 jRuby on Rails 설정

약간의 삽질(오전을 날렸음) 끝에 Migration을 돌릴 수 있었다.

준비물
  1. NetBeans IDE 6.0 M10 - 이후 버전이면 뭐라도 상관없음.
  2. JDBC Driver
  3. 윈도우만 설치한 컴퓨터

이정도면 준비 오케이.

아무생각 없이 NetBeans를 와장창 깔아버린다.

JDK 6.0, GlassFish(WAS), Derby(DB), jRuby 까지 설치.

새 프로젝트로 jRuby On Rails를 만들고 모델을 만든 후 Migration 을 시도하니 오류발생

검색을 좀 해보니 environment.rb를 수정해야 한다고 한다.

require File.join(File.dirname(__FILE__), 'boot')

if RUBY_PLATFORM =~ /java/

require 'rubygems'

RAILS_CONNECTION_ADAPTERS = %w(jdbc)

end

Rails::Initializer.run do config

붉은 색 부분을 추가한다. jRuby랑 호환을 위해 RUBY_PLATFORM 을 따지나보다.

jRuby에 JDBC를 사용하기로 했으니 database.yml도 수정

development:

adapter: jdbc

driver: com.mysql.jdbc.Driver

url: jdbc:mysql://localhost:3306/jruby

username: root

password:

인코딩 문제가 있을 것도 같지만 일단 패스.

다시 Migration 하니...

안된다.

com.mysql.jdbc.Driver 드라이버 자체를 로드를 못한다.

디폴트 설치 기준으로

C:\Program Files\NetBeans 6.0M10\ruby1\jruby-1.0\lib

에 jdbc 파일을 복사한다. mysql-connector-java-5.0.7-bin.jar 를 툭 떨어뜨리기.


(in D:/wrkz/IDS/workspace2/ror1)
== CreateBasicwords: migrating
================================================
--
create_table(:basicwords)
-> 0.1250s
== CreateBasicwords:
migrated (0.1250s) =======================================
==
CreateStandardwords: migrating
=============================================
--
create_table(:standardwords)
-> 0.1400s
==
CreateStandardwords: migrated (0.1400s) ====================================

와하하하 잘된다.
자료가 없는 것에 비해 금방 적응해서 다행.

.....이라고 생각했으나

역시 mysql 인코딩 문제가 발생
한글이 ??로 전부 깨진다.
이래저래 삽질해보다가 결국 mysql 을 꼭 쓸 필요가 있는가 하는 질문을 던져보고
만일 mysql 때문인지 jRuby 때문에 안되는지 확실하게 알려면 다른 DB를 써보면 된다라는 결정을 내리고 sqlite(파일 하나만 덜렁 만들어서 완소) 도전.

잘 안된다.

기본으로 NetBeans와 함께 설치하는 Derby를 사용해보기로 했다.
development:
adapter: jdbc
driver: org.apache.derby.jdbc.ClientDriver
url: jdbc:derby://localhost:1527/sample
username: app
password: app

아무 옵션도 안만진 상태에서 요렇게
적용해보니 잘 된다.
한글도 문제 없다.

그나저나 콘솔창에서 한글 입력이 깨지는 문제는 어쩐다지.

2007/03/26

완전소중 Blogger!

그동안 별로 신경 안쓰고 있었는데 beta딱지가 떨어지면서 너무 좋아진 Blogger!

트랙백 기능이 없어 이상하다고 생각했으나 HaloScan의 동영상을 보면서 쉽게 올릴 수 있었다.
귀찮아도 역시 템플릿을 html 형식으로 지원하고 script가 먹는 쪽이 좋다. ;)

파일 첨부도 이런식으로 어딘가에 할 수 있지 않을까나;;