2018년 3월 5일 월요일

자바스크립트 정규식을 이용한 DOM 객체 클래스 삭제 방법

$('.evtPop').find('.img').removeClass(function (idx, className) {
  console.log('클래스삭제', idx, className);
  return className.match(/win\d/).join(' ');
})

[clojure][designpattern] 반복자패턴 (Iterator pattern)

일단 자바
Iterator i;
while (i.hasNext()) {
  i.next();
}

Node next = root;
while( next != null )
  next = next.next;

클로저에서 반복자에 해당하는 것
(seq [1 2 3]) => (1 2 3)
(seq (list 4 5 6)) => (4 5 6)
(seq #{ 7 8 9}) => (7 8 9)
(seq (int-array 3)) => (0 0 0)
(seq "abc") => (\a \b \c)

시퀀스인가? 반복자는 단순 시퀀스이다.
(first (seq [1 2 3]))
; 1
(rest (seq [1 2 3]))
; (2 3)
시퀀스가 아닌 것으로도 이렇게 돌아다닐 수 있나? 클로저는 자바다. 인터페이스를 구현하면 된다.

(deftype RedGreenBlackTree [& elems]
clojure.lang.Seqable
(seq [self]
;; traverse element in needed order
))

내 생각에는 그냥 죄다 시퀀스로 쓰면 될 것 같다.

[hackerrank][java8][clojure] SolveMeFirst

int 두개 더하기
java
static int solveMeFirst(int a, int b) {
  return a + b;     
}
clojure
(defn solveMeFirst [x y]    
    (+ x y))
여기서 특이한 점은 stdin, stdout 방법을적어놔야할 것 같다. 자바
Scanner in = new Scanner(System.in);
int a = in.nextInt();
int b = in.nextInt();
int sum = solveMeFirst(a, b);
System.out.println(sum);
클로저
(def a (read-line))
(def b (read-line))

(println (solveMeFirst (Integer/parseInt a) (Integer/parseInt b)))

[python][hackerrank] Sherlock and Squares


https://www.hackerrank.com/challenges/sherlock-and-squares/problem
import math

q = int(input().strip())
for _ in range(q):
    a, b = map(int, input().strip().split(' '))
    _start = math.ceil((math.sqrt(a)))
    ret = 0
    while _start**2 <= b:
        ret += 1
        _start += 1
    print(ret)

[clojure][designpattern]책임 연쇄(Chain Of Responsibility) 패턴

비속어를 별표로 변하는 필터를 만들자.
public abstract class Filter {
  protected Filter nextFilter;

  abstract void process(String message);

  public void setNextFilter(Filter nextFilter) {
    this.nextFilter = nextFilter;
  }
}
실제 적용할 필터
class LogFilter extends Filter {
  @Override
  void process(String message) {
    Logger.info(message);
    if (nextFilter != null) nextFilter.process(message);
  }
}

class Profanityfilter extends Filter {
  @Override
  void process(String message) {
    String newMessage = message.replaceAll("fuck","f*ck");
    if (nextFilter != null) nextFilter.process(newMessage);
  }
}

class RejectFilter extends Filter {
  @Override
  void process(String message) {
    System.out.println("RejectFilter");
    if (message.startsWith("[A Project NY]")) {
      if (nextFilter. != null) nextFilter.process(message);
    }
  }
}

class StatisticsFilter extends Filter {
  @Override
  void process(String message) {
    Statistics.addUsedChars(message.length());
    if (nextFilter != null) nextFilter.process(message);
  }
}
1. 각 필터를 만든다. 2. 서로 기차놀이처럼 연결한다. (순서를 만드는 것이다)
Filter rejectFilter = new RejectFilter();
Filter logFilter = new LogFilter();
Filter profanityFilter = new ProfanityFilter();
Filter statsFilter = new StatisticsFilter();

rejectFilter.setNextFilter(logFilter);
logFilter.setNextFilter(profanityFilter);
profanityFilter.setNextFilter(statsFilter);

String message = "[A PROFIT NY] What the fuck?";
rejectFilter.process(message);
clojure 클로저는 각 필터를 함수로 만든다.
;; define filters

(defn log-filter [message]
  (logger/log message)
  message)

(defn stats-filter [message]
  (stats/add-used-chars (count message))
  message)

(defn profanity-filter [message]
  (clojure.string/replace message "fuck" "f*ck"))

(defn reject-filter [message]
  (if (.startsWith message "[A Profit NY]")
    message))
(defn chain [message]
  (some-> message
          reject-filter
          log-filter
          stats-filter
          profanity-filter))
저 some->가 뭐지? some->는 ->와 기능이 같다.
한가지만 빼고 표현식이 nil이면 멈춘다. 그리고 nil을 내뱉는다. nil이 아니면 값을 다음에 넘긴다.
(chain "fuck") => nil
(chain "[A Profit NY] fuck") => "f*ck"
[A profit NY] 가 없으면 reject-filter에서 이미 걸려서 nil이 나옴.

[algorithm] 선택정렬 (selction sort with C and Python)

선택정렬 C언어와 파이썬 비교

main.c

#include 
#include 

#include "selection_sort.h"

void printArray(int value[], int count);

int main()
{
    int values[] = { 80, 75, 10, 60, 15, 49, 12, 25 };
    int count = sizeof(values)/sizeof(int);

    printArray(values, count);

    printf("\n선택 정렬이 시작됩니다 \n");
    selection_sort(values, count);

    printArray(values, count);

    return 0;
}
void printArray(int value[], int count)
{
    int i = 0;
    for(i = 0; i < count; i++) {
        printf("%d ", value[i]);
    }
    printf("\n");
}

selection_sort.h

#ifndef SELECTION_SORT_H_INCLUDED
#define SELECTION_SORT_H_INCLUDED

void selection_sort(int value[], int count);

#endif // SELECTION_SORT_H_INCLUDED

selection_sort.c

2018년 2월 17일 토요일

[리뷰] 파이썬을 좋아하면 누구나 읽어보아야할 [Head First Python]


아주 좋은 책이다.

잘 짜여진 이야기를 풀어나가는 것처럼 술술 나아간다. 분명 이렇게 만들기 위해 여러번 고쳐썼을 것이다.

헤드퍼스트 특유의 만담은 파이썬을 더 잘 이해하게 해주고

setuptools를 사용하여 간단한 모듈을 만들어보는 것도 멋졌다.

python의 깊은 내용은 알 수 없었지만, 파이썬을 만나볼 수 있었다.

책을 다보면 나도모르게 web개발을 할 수 있을 정도의 연결고리를 만들어준다.

알게모르게 배워야 하는 것들을 다 배운 것 같다.

파이썬에 대해 알고 싶은 사람들은 다른 책보다
일단 헤드퍼스트 파이썬을 먼저 만나서
파이썬이 무엇인지 파이썬이 무엇을 추구하는지
알아보고 다른 정보들을 접하기를 추천한다.

Head First Python URL : http://www.hanbit.co.kr/store/books/look.php?p_code=B1306099216

2018년 2월 8일 목요일

[python][algospot] 울타리 잘라내기

구종만의 알고리즘 문제해결 책을 본 후 파이썬으로 짜봤다.
def brute_force(h):
    ret = 0
    N = len(h)
    for left in range(N):
        minHeight = h[left]
        for right in range(left, N):
            minHeight = min(minHeight, h[right])
            ret = max(minHeight*(right-left+1), ret)
    return ret

print(brute_force([7,1,5,9,6,7,3]))
print(brute_force([1,4,4,4,4,1,1]))

def divide_conquer(h):
    def solve(left, right):
        if left == right: return h[left]

        # 이 둘이 중요.
        mid = (left + right) // 2  # divide
        ret = max(solve(left, mid), solve(mid+1, right))  # divide and conquer

        lo , hi = mid, mid+1  # 중앙에 걸치는 녀석들을 잡기 위해
        height = min(h[lo], h[hi])  # 중앙에서 낮은 판자높이를 구함. (초기값)
        ret = max(ret, height*2)  # [mid,mid+1]만 포함하는 너비 2인 사각형 고려

        # 후처리작업 병합정렬처럼 반으로 잘라서 각개격파를 했지만
        # 병합정렬과는 다르지만 부족한 면을 반복문으로 메꾸는 것.
        # 사각형이 입력 전체를 덮을 때까지 확장한다.
        while (left < lo or hi < right):
            # 더 높은 판자를 향해 확장한다. (낮은 판자로 가면 최대값을 구할 수 없다.)
            if (hi < right and (lo == left or h[lo-1] < h[hi+1])):
                hi += 1
                height = min(height, h[hi])
            else:
                lo -= 1
                height = min(height, h[lo])
            ret = max(ret, height*(hi-lo+1))

        return ret
    return solve(0, len(h)-1)


print('divide_conquer')
print(divide_conquer([7,1,5,9,6,7,3]))
print(divide_conquer([1,4,4,4,4,1,1]))

[python][hackerrank] Jumping on the Clouds: Revisited

아직은 역시 웜업 단계인가 보다.
쉽다.
n, k = tuple(map(int, input().strip().split(' ')))
c = tuple(map(int, input().strip().split(' ')))

result = 100
tmp = 0

while True:
    tmp = (tmp + k) % n
    result -= (1 + c[tmp]*2)
    if tmp == 0:
        break
    
print(result)

2018년 2월 6일 화요일

[python][hackerrank] Sequence Equation

처음에는 리스트로 그냥 뿌려서 하면 되는 건가 했는데
해(OUTPUT)를 가지고 반대로 x값(INPUT)을 구하는 것이었다.
값이 없는 경우가 있다면 그것들을 어떻게 해야 하는지 설명이 필요한데 그에 대한 설명이 없어서
그런경우는 없다는 가정하에 문제를 풀었다.

그래서 미리 p(p(y))를 풀어서 key값에 넣고 그 안에 x(INPUT)값을 value로 넣었다.

n =  int(input())
n_list = list(map(int, input().strip().split(' ')))
p = { n_list[n_list[x-1]-1]:x for x in n_list}

for i in range(1, n+1):
    print(p[i])

[python][hackerrank] Circular Array Rotation

n은 배열 값의 수
k는 right-circular-rotation의 횟수
q는 질의 회수
m은 실제 배열의 값

from collections import deque

n, k, q = map(int, input().strip().split(' '))
m = deque(map(int, input().strip().split(' ')))  # integers
m.rotate(k)  # wow...

for m_i in range(q):
    print(m[int(input())])  # don't need strip(). int() will do this.

혹은 다른 방법을 사용해보자.

n, k, q = map(int, input().strip().split(' '))
m = list(map(int, input().strip().split(' ')))

k %= n; tmp = m[-k:]; del m[-k:]; m[0:0] = tmp

for m_i in range(q):
    print(m[int(input())])  # don't need strip(). int() will do this.

[clojure][designpattern] 프로토타입 패턴

프로토타입은 원형틀이라고도 볼 수 있다.
기본적으로 만들어진 틀을 사용하는 것이다.
내용에서는 회원등록양식을 사용했는데 그 틀에 대한 기본틀을 프로토타입이라 하자. 여기서는 몸무게를 적지 않으면 60킬로를 기본값으로 넣는다고 한다.
그리고 중요한 것은 clone()메소드인데 왜 중요하냐면 기존에 만들어진 틀을 아주 쉽게 복사할 수 있는 것이다.

public class RegistrationForm implements Cloneable {
  private String name = "Zed";
  private String email = "zzzed@gmail.com";
  private Date dateOfBirth = new Date(1990, 1, 28);
  private int weight = 60;
  private Gender gender = Gender.MALE;
  private Status status = Status.SINGLE;
  private List children = Arrays.asList(new Child(Gender.FEMALE));
  private double monthSalary = 1000;
  private List favouriteBrands = Arrays.asList("Adidas", "GAP");

  @Override
  protected RegistrationForm clone() throws CloneNotSupportedException {
    RegistrationFrom prototyped = new RegistrationForm();
    prototyped.name = name;
    prototyped.email = email;
    prototyped.dateOfBirth = (Date)dateOfBirth.clone();
    prototyped.weight = weight;
    prototyped.gender = gender
    prototyped.status = status;

    List childrenCopy = new ArrayList();
    for (Child c : children) {
      childrenCopy.add(c.clone());
    }
    prototyped.children = childrenCopy;
    prototyped.monthsCopy = monthSalary;

    List brandsCopy = new ArrayList();
    for (String s : favoriteBrands) {
      brandsCopy.add(s);
    }
    prototyped.favouriteBrands = brandsCopy;
    
    return prototyped;
  }
}
사용자를 만들 때마다, clone()을 호출해서 기본값으로 쓴다.
왜 clone()을 사용해야 하나? 바로 자바가 나를 죽어라 헷갈리게 한 내용인 카피 문제이다.
이것 때문에 나는 getter를 만들때도 그것이 객체라면 복사를 한다. (혹시 몰라서...)


Clojure

(def registration-prototype
  {:name "Zed"
   :email "zzzed@gmail.com"
   :date-of-birth "1970-01-01"
   :weight 60
   :gender :male
   :status :single
   :children [{:gender :female}]
   :month-solary 1000
   :brands ["Adidas" "GAP"]})

;;return new object
(assoc registration-prototype
  :name "WHO"
  :email "EMAIL@DOTCOM"
  :weight 52
  :gender :female
  :month-salary 0)
clojure는 기본적으로 불변객체이기 때문에 clone은 필요없다.
그렇다면 항상 다 모든것을 final로 만들어 복사하면 느려지지 않을까?
느리긴 한데... 아주 느리지는 않다는 것이 클로저들의 주장인 것같다.

[python][hackerrank] Save the Prisoner!

#!/bin/python3
def saveThePrisoner(n, m, s):
    res = (m + s - 1) % n
    if res == 0:
        res = n
    return res

t = int(input().strip())
for _ in range(t):
    n, m, s = [int(x) for x in input().strip().split(' ')]
    result = saveThePrisoner(n, m, s)
    print(result)