2014년 1월 9일 목요일

베뉴 프로의 SD Card 종류에 따른 속도 제한

베뉴 11 프로를 장만한 김에 sd 카드도 하나 구입하려고 해서 알아보다가
베뉴 자체의 리더기 성능에 제한이 있다는 사실을 알았다.

베뉴 8 프로와
베뉴 11 프로 5130 모델은
UHS-I 를 지원하지 않는다.
그리고 읽기/쓰기가 최대 25MB/s (200 Mb/s)
까지가 한계라고 한다.

즉, sd 카드 속도가 100MB/s 를 지원하던, 25MB/s 까지 지원하던
내가 실제로 쓸 수 있는 속도는 25MB/s 라는 소리다.

내가 개인적으로 싫어하는 산*스크는 빼고,
나머지 제품들에서 64GB 짜리 sd  카드를 찾아봐야겠다.

아래는, 모델에 따른 지원형식과 속도를 보여주는 표이다.

TabletInterfaceCard typeBus speedSpec Version
Venue 8 ProHigh SpeedSD, SDHC, SDXC25 MB/s2.00
Venue 11 Pro 5130High SpeedSD, SDHC, SDXC25 MB/s2.00
Venue 11 Pro 7130/7139UHS-ISDHC, SDXC50MB/s (SDR50, DDR50)
104 MB/s (SDR104)
3.01
참조 사이트: 델 Support

2013년 12월 10일 화요일

소프트 키보드가 켜졌는지 안켜졌는지 확인하는 법

제일 상위루트의 레이아웃뷰에 id를 붙입니다. (여기선 activityRoot)
그 후 그 뷰를 코드에서 불러내어 ViewTreeObserver의 OnGlobalLayoutListener를 붙입니다.
흠 100프로 정확한 방법은 아니지만 현재 방법이 이것밖엔 없네요
final View activityRootView = findViewById(R.id.activityRoot);
activityRootView.getViewTreeObserver().addOnGlobalLayoutListener(new OnGlobalLayoutListener() {
    @Override
    public void onGlobalLayout() {
        int heightDiff = activityRootView.getRootView().getHeight() - activityRootView.getHeight();
        if (heightDiff > 100) { // if more than 100 pixels, its probably a keyboard...
            ... do something here
        }
     }
});
참고:
http://stackoverflow.com/questions/2150078/how-to-check-visibility-of-software-keyboard-in-android

HashBiMap (쌍방향 해쉬맵) - Guava 라이브러리

가끔 이럴 때 있지 않나요?
키 값과 데이터를 넣는데,
둘 다 겹치지 않는 값이였으면 좋겠다 싶을 때.

이럴 때 구글의 구아바(Guava) 라이브러리 중 HashBiMap 을 써보는 것도 좋은 선택이 될 것 같네요.

일대일 대응을 하는 해쉬맵입니다.

다른 점은:
  1. K (key) 값이 같을 경우에는 새로 들어온 값으로 덮어씁니다.
  2. V (value) 값이 같을 경우에는 익셉션 IllegalArgumentException 을 throw 합니다.

간단한 사용법을 알아봅시다.

구아바 라이브러리를 직접 받아서 쓰시거나
안드로이드라면 build.gradle 의 dependencies 에
compile group: 'com.google.guava', name: 'guava', version: '15.0'
를 넣어주시면 maven 에서 import 를 해 줍니다.

해쉬맵을 생성하려면
HashBiMap<K, V> hashBiMap = HashBiMap.create();
를 해 주시면 됩니다.

일반적인 HashMap 처럼
값을 넣을때에도
hashBiMap.put(K, V);
하시면 됩니다.

마지막으로,
hashBiMap.inverse();
하실경우엔 K 와 V 가 서로 반대로 되어서 나옵니다. (일대일 대응이기 때문에 가능하죠)

2013년 12월 4일 수요일

장고 무작정 시작하기 - Pip을 이용한 설치편


  1. 파이썬 설치하기
  2. pip 설치하기
  3. 장고 설치하기


이번엔 Pip을 이용하여 장고를 설치해 보도록 하겠습니다.

1. 파이썬 설치하기
장고를 설치하기에 앞서
파이썬을 설치하겠습니다.
장고는 파이썬 2.6~, 그리고 3.x 에서 다 작동합니다.
저는 파이썬 3.x 를 기준으로 작성을 하겠습니다.

윈도우에서
윈도우 사용자라면
에 들어가서 Windows MSI 인스톨러를 받읍시다.
(2013년 11월 22일 기준)
파이썬 3.3.3버전
이 있네요.

파일을 받아서 설치한 후에
명령창을 켜서 python
을 입력해 봅시다.
만약 명령어가 되지 않으면 환경 변수 설정을 해주셔야 하는데요
PATH 변수에 C:\파이썬설치경로
을 추가해 주시면 됩니다. 다른 여러 곳에 자세한 설명들이 많으니 이것은 패스하도록 하겠습니다.

맥에서
맥 이라면 기본으로 파이썬 2.7 버전이 깔려있을 것입니다.
파이썬 3.x 버전을 깔고 싶으신 분들은
Homebrew 를 이용하시는 걸 추천드릴께요.
맥 쓰시는 분들이면 이미 많이들 쓰시지 않을까 싶은데
터미널에 가셔서
ruby -e "$(curl -fsSL https://raw.github.com/mxcl/homebrew/go/install)"
라고 입력하시면 brew 가 깔리고
brew install python3

를 입력하시면 파이썬이 깔리며, python3 라고 명령어를 치면 python 3.x 버전이, python 을 치시면 맥에 깔린 기본 python 2.7 버전이 실행됩니다.

2. Pip (Python Indexing Project) 설치하기
이제 파이썬의 여러 패키지들을 편하게 설치/삭제 시켜주는 셋업툴을 받아야하는데 그것은 바로 pip 이라 불리는 파이썬 패키지입니다.

Window 에서는
pip을 설치하기위해서는 setuptools 라는 패키지가 필요합니다.
그래서 먼저 setuptools를 설치해주셔야 하는데요
http://www.pip-installer.org/en/latest/installing.html
에 들어가셔서 ez_setup.py 를 받으시거나
ez_setup.py 링크를 누르셔서
텍스트에 붙여넣으신후 이름대로 저장!

그 위치에서 커맨드창을키고  python ez_setup.py
를 해주시면 설치가 됩니다.

그후,
https://pypi.python.org/pypi/pip
에 들어가셔서 초록색 버튼의 Download를 눌러주신후 파일의 압축을 풀면되는데요
해당 경로에들어가셔서
python setup.py install

을 입력해 주시면 되겠습니다.

Mac 에서는
brew 를 설치하셨다면
brew install pip

만 해주시면 됩니다.

3. Django 설치하기
pip 설치를 한 이상 장고의 설치는 간단하죠!
pip install django

만 하면 됩니다.


2013년 12월 1일 일요일

아수스 T100 한국 깡패 가격. 이것이 한국 프리미엄 가격인가?

아실만한 분들은 아시겠지만,
전자기기들은 한국에만 오면 가격이 뻥튀기 되죠. (국내/외 기업에 관계없이... 삼성너말이다)

아톰 베이 트레일 코어 출시이후

새로이 선보여지고 있는 윈도우 8 태블릿들 중
관심을 많이 받고있는 제품 중 하나인 아수스 T100 이
한국에도 정식 발매를 하는데요

본체에 USB 3.0, HDMI 까지 달리고
, 키보드, 독 까지 다 포함한 가격이
처음 출시 시 380 달러 정도, 블랙 프라이데이 때 299 달러에 판매된 제품이

한국에서는... 정발 가격이
69만 9000원 이라고 합니다.
다음은 공식 사이트에서 가져온 내용입니다.

http://asusblog.co.kr/140201806951





블로그 댓글들에서
아주 난리가 났네요.
이 가격이면 미국에서는 t100 2 대를 살 수 있겠네요...

더 놀라운 건
권장 소비자가격을 상회하는 가격으로 마트에서 팔리고 있다는 점이죠...


보이시나요??
출고가가 101만 8천원인데 89만 9천원으로 할인해서 판다는 내용입니다.
어후... 울트라북 한대를 살 가격이군요..
애초에 인텔에서 저렴한 가격으로 내놓은 코어가 베이 트레일 인데 말입니다.

합리적인 가격에 사고싶으시다면 구매대행 사이트나 공동구매를 하시기 바랍니다...





2013년 11월 21일 목요일

장고 무작정 시작하기 - 시작하기에 앞서

이 글은 Django Project  사이트 튜토리얼을 참조하여 쓰는 글입니다. 저도 아직 초보자임을 미리 밝힙니다.

장고를 시작하기에 앞서
장고의 장점들을 알아봅시다

1. 모델(데이타베이스 스키마) 디자인이 편하다
물론 웹사이트를 데이터베이스 없이 만들수도 있지만, 필요하다면 간편하게 모델을 만들 수 있습니다.

예:

from django.db import models

class Reporter(models.Model):
    full_name = models.CharField(max_length=70)

    # On Python 3: def __str__(self):
    def __unicode__(self):
        return self.full_name

class Article(models.Model):
    pub_date = models.DateField()
    headline = models.CharField(max_length=200)
    content = models.TextField()
    reporter = models.ForeignKey(Reporter)

    # On Python 3: def __str__(self):
    def __unicode__(self):
        return self.headline
이렇게 객체 클래스를 선언하듯이 선언하여 모델을 만들 수 있는데
이것을 object-relational mapping 이라고 하고, 이것은 mysite/news/models.py
에 저장됩니다.

2. 쉽게 여기저기서 작업할 수 있다.
프로젝트 파일들로 구성되어있기 때문에, 파일만 들고와서
파이썬 명령어로 서버를 구동시키기만 하면 구동됩니다.

3. 에러를 확인하기가 매우 쉽다..
콘솔창과 브라우져에서 어떤 에러가 떴는지, 어디서 에러가 발생하였는지 보여주는데다가,
고친 부분이 바로바로 적용됩니다. (DB 를 제외하고)
그리고 콘솔창에서 파이썬 명령어로 미리 어떤 결과가 나올지 볼 수도 있습니다.
개인적으로 저 또한 웹 만들어보는 것을 처음 해 보았기에, 가장 마음에 드는 점이였습니다.

이 외에도 좋은 점들이 매우 많지만(원하는 URL 지정, 템플릿 만들기, 원하는 뷰 만들기 등)
처음 하시는 분들은 잘 모르실테니 필자도 잘 모릅니다
직접 장고를 해 보면서 알아가도록 합시다.

참고로, 장고를 기반으로 만든 사이트들은
Disqus, 인스타그램, 핀터레스트 등이 있습니다.


참조한 글:
https://docs.djangoproject.com/en/1.6/intro/overview/

2013년 11월 17일 일요일

Google Volley 의 기능들과 사용법 (코드 예제)


Volley의 주 기능과 장점

* 하나의 requestQueue 모든 요청들을 처리한다
     -알아서 동시다발적으로 요청을 할수있다

* 우선 순위 설정을 할수 있다.
     -이미지 파일들은 기본적으로 낮은 우선순위를 가진다.
     -Priority class 를 상속하여 우선순위를 customize 할 수도 있다.

* 리퀘스트를 취소할 수도 있다. ( ListView 에서 유저가 빠르게 스크롤링 할 경우, 스크롤링 한 내용을 다 로딩할 필요가 없고, 보여지는 부분 이외에 로딩이 안된 리퀘스트들은 취소할 수 있다. )
      -Volley 가 알아서 자동으로 처리한다.

* 프로요 버전의 HttpURLConnection에 있는 버그를 해결해준다.


* NetworkImageView 클래스가있다.

     -imageLoader 구현
     -이미지로딩 요청들을 모았다하 하나로 묶어서 보내준다.
     -캐싱 기능
     -이미지 스케일링 기능 (훨씬 빠른 로딩이 가능하다)
     -병행 (동시다발적) 이미지 로딩 - 핸드폰의 코어수 만큼의 로딩하여 최적화 함.

Volley 가 작동하는 법!

     



처음 리퀘스트를 생성하고 큐에 넣으면, 우선순위에 맞추어 캐시 큐로 들어간다.
그 후, 리퀘스트가 큐에서 나올 차례가 되면, CacheDispatcher 가 리퀘스트를 빼간다.
그럼 Volley는 리퀘스트에 대한 결과값이 캐시에서 가져올 수 있는지 확인한다. (hit 화살표)
만약 가져올수 없으면 miss 다. (miss 화살표)

캐시 hit 의 경우, 캐시에서 결과 값을 읽어온 후 파싱을 하고 response를 던진다.

miss 의 경우, NetworkResponse에서 리퀘스트를 받아서 넷상으로 request를 보내고 결과 값을 받아 파싱한다.

코드 예제
Volley를 쓰려면 기본적으로 3 단계를 거친다.:
1. RequestQueue  를 만든다.
2. Reuest를 만든다.
3. Request를 RequestQueue 에 넣는다.

1. RequestQueue 를 Singleton 형식으로 만든다.
Volley는 하나의 Queue에서 모든 요청을 처리하므로, Queue는 하나만 만들어 쓰면 되기에 Singleton 패턴을 쓴다.


public class VolleySingleton {
    private static VolleySingleton mInstance = null;
    private RequestQueue mRequestQueue;
    private ImageLoader mImageLoader;

    private VolleySingleton(Context context){
        mRequestQueue = Volley.newRequestQueue(context);
        mImageLoader = new ImageLoader(this.mRequestQueue, new ImageLoader.ImageCache() {
            private final LruCache mCache = new LruCache(10);
            public void putBitmap(String url, Bitmap bitmap) {
                mCache.put(url, bitmap);
            }
            public Bitmap getBitmap(String url) {
                return mCache.get(url);
            }
        });
    }

    public static VolleySingleton getInstance(Context context){
        if(mInstance == null){
            mInstance = new VolleySingleton(context);
        }
        return mInstance;
    }

    public RequestQueue getRequestQueue(){
        return this.mRequestQueue;
    }

    public ImageLoader getImageLoader(){
        return this.mImageLoader;
    }
}

2. Http Request를 구현한다.
1)미리 Type이 정의된 리퀘스트의 경우
생성자 파라미터로  int Request.Method.(GET or POST), String url, T Content, Response Listener, Response ErrorListener 를 받는다.
new JsonObjectRequest( //JsonArrayRequest and StringRequest(call API in URI) is the same
                Request.Method.POST, "url", null,
                new Response.Listener() {
                    @Override
                    public void onResponse(JSONObject jsonObject) {

                    }
                },
                new Response.ErrorListener() {
                    @Override
                    public void onErrorResponse(VolleyError volleyError) {

                    }
                }
        );
    };
2)커스텀 Request (JsonRequest or Request)의 경우
      1 - JsonRequest는 parsenetworkResponse 메소드에서 결과값인 NetworkResponse를 파싱 해주어야 한다.

    JsonRequest jsonRequest = new JsonRequest(Request.Method.POST, "url", "requestBody",
            new Response.Listener() {
                @Override
                public void onResponse(JSONArray jsonArray) {

                }
            },
            new Response.ErrorListener() {
                @Override
                public void onErrorResponse(VolleyError volleyError) {

                }
            })
    {
        @Override
        protected Response parseNetworkResponse(NetworkResponse networkResponse) {
            try{
                String json = new String(networkResponse.data, HttpHeaderParser.parseCharset(networkResponse.headers));
                return Response.success(
                        new JSONArray(json), HttpHeaderParser.parseCacheHeaders(networkResponse)
                );
            }
            catch(UnsupportedEncodingException e){
                return Response.error(new ParseError(e));
            }
            catch(JSONException e){
                return Response.error(new ParseError(e));
            }
        }
    };
-2 Request 의 경우에도 parseNetworkResponse 에서 파싱을 해주고, deliverResponse에서 Response 리스너가 반응하는 함수를 넣어주어야 한다.

    Request integerRequest = new Request(Request.Method.POST, "url", new Response.ErrorListener() {
        @Override
        public void onErrorResponse(VolleyError volleyError) {

        }
    }) {
        @Override
        protected Response parseNetworkResponse(NetworkResponse networkResponse) {
            try {
                Integer i = new Integer(new String(networkResponse.data, HttpHeaderParser.parseCharset(networkResponse.headers)));
                return Response.success(i, HttpHeaderParser.parseCacheHeaders(networkResponse));
            } catch (UnsupportedEncodingException e) {
                e.printStackTrace();
            }
        }

        @Override
        protected void deliverResponse(Integer integer) {
             listener.onResponse(integer);
        }
    };
3) 이미지 요청은 URL 과 위의 Singleton 에 있는 ImageLoader를 이용하여 요청한다.
    ImageRequest a = new ImageRequest("url", new Response.Listener() {
        @Override
        public void onResponse(Bitmap bitmap) {

        }
    }, /*maxWidth*/0, /*maxHeight*/ 0, Bitmap.Config.ARGB_8888, new Response.ErrorListener() {
        @Override
        public void onErrorResponse(VolleyError volleyError) {
        }
    });
또는 XML 레이아웃파일에 com.android.volley.toolbox.networkimageview 를 넣어놓고 Java에서 뷰를 부른 후, 아래와 같은 형식으로 요청한다.
    mImageView.setImageUrl(URL, mImageLoader);
(자동으로 큐에 들어가므로 더욱 간단하다.)

3. 생성한 Request를 큐에 넣는다.
VolleySingleton.getInstance(mContext).getRequstQueue().add(request);


참고 자료:
     Youtube - Google I/O 2013 - Volley: Easy, Fast Networking for Android
                    http://www.youtube.com/watch?v=yhv8l9F44qo
     Setting up the Android Google Volley ImageLoader for NetworkImageView
          http://cypressnorth.com/mobile-application-development/setting-android-google-volley-imageloader-networkimageview/ 
     [android] Volley - Network & ImageLoading 라이브러리 ( google I/O 2013 )     
          http://hanburn.tistory.com/135