반응형

일반적인 map.size() 말고 실제 메모리에 올라가는 map byte사이즈를 알고 싶은경우~


다음과 같이 사용하면 될듯


public static void size(Map map) {
try {
System.out.println("Index Size: " + map.size());
ByteArrayOutputStream baos=new ByteArrayOutputStream();
ObjectOutputStream oos=new ObjectOutputStream(baos);
oos.writeObject(map);
oos.close();
System.out.println("Data Size: " + baos.size());
} catch(IOException e){
e.printStackTrace();
}
}


baos.size() 메소드를 들어가보면 다음과 같이 bytes를 리턴한다.

/**
* Returns the current size of the buffer.
*
* @return the value of the <code>count</code> field, which is the number
* of valid bytes in this output stream.
* @see java.io.ByteArrayOutputStream#count
*/
public synchronized int size() {
return count;
}


확인할일이 있어서 보다가 정리

반응형
반응형

자바 Stream에서 Map, Object내부에 또 다른 Map, Set, List와 같은 Collection이 있을 때 각 value를 개별된 값으로 처리하고 싶은 경우



Student POJO

public class Student {

private String name;
private Set<String> book;

public void addBook(String book) {
if (this.book == null) {
this.book = new HashSet<>();
}
this.book.add(book);
}
//getters and setters

}



flatMap() and Set example

1차적으로 map으로 POJO에 Set에 담긴 Book데이터를 가져와 flatmap으로 펼친 후 list로 collect

import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;

public class TestExample2 {

public static void main(String[] args) {

LexiconMain.Student obj1 = new LexiconMain.Student();
obj1.setName("mkyong");
obj1.addBook("Java 8 in Action");
obj1.addBook("Spring Boot in Action");
obj1.addBook("Effective Java (2nd Edition)");

LexiconMain.Student obj2 = new LexiconMain.Student();
obj2.setName("zilap");
obj2.addBook("Learning Python, 5th Edition");
obj2.addBook("Effective Java (2nd Edition)");

List<LexiconMain.Student> list = new ArrayList<>();
list.add(obj1);
list.add(obj2);

List<String> collect =
list.stream()
.map(x -> x.getBook()) //Stream<Set<String>>
.flatMap(x -> x.stream()) //Stream<String>
.distinct()
.collect(Collectors.toList());

collect.forEach(x -> System.out.println(x));
}

}


Output

Spring Boot in Action
Effective Java (2nd Edition)
Java 8 in Action
Learning Python, 5th Edition


Stream관련 자세한 예제가 더 궁금하다면 아래 링크로


참고 : https://www.mkyong.com/java8/java-8-flatmap-example/

반응형
반응형


현상황  : Cloudera(클라우데라) 버전(CDH 5.5.1, Parcel), Spark버전(1.5) - jdk version 1.7

필요상황 : 기존 작업을 Spark1.5(jdk1.7) - jdk 1.8로 돌리기

준비상황 :  클러스터의 각 노드들에 jdk1.8이 설치되어 있어야 함.


spark-submit스크립트에 jdk1.8 path를 명시

--conf "spark.yarn.appMasterEnv.JAVA_HOME=/home1/irteam/jdk/jdk1.8.0_141" \
--conf "spark.driverEnv.JAVA_HOME=/home1/irteam/jdk/jdk1.8.0_141" \
--conf "spark.executorEnv.JAVA_HOME=/home1/irteam/jdk/jdk1.8.0_141" \

이렇게 driver와 executor의 JAVA_HOME은 명시가 되었고

해당 스크립트가 돌아가는 client의 JAVA_HOME은 export로 변경해준다.


기존 단순 spark-submit명령어에서 앞에 다음과 같이 추가

export JAVA_HOME=/home1/irteam/jdk/jdk1.8.0_141 && spark-submit \


이렇게 설정을 해주게 되면 jdk1.8로 빌드된 코드도 기존 spark로 돌릴 수 있게 된다.


이런식의 설정으로 클라우데라 스파크 버전 또한 2점대로 높여 사용할 수 있겠다.


반응형
반응형


  • 솔직함이란 감정에 따라 일어난 생각을 숨기지 않고, 타인을 의식하지 않으며 자연스럽게 표현하는 성향이다. 그렇게 할 수 있는 이유는 평소 좋은 마음 상태를 유지하려고 노력해왔고 그로 인한 자신의 선한 의지에 대해 어느 정도 확신을 가지고 있기 때문이다. 그리고 선한 의지를 바탕으로 한 솔직함은 사람과 사람을 보다 깊은 곳에서 연결해준다.
  • '아, 나만 이런 이상한 생각을 한 건 아니었구나.' 상대로부터 제대로 이해받고 있다고 느낄 때 드는 안도감과 충족감. 그런 감정을 주고받을 수 있는 사이는 서로에게 깊은 친밀감을 가진다.
  • 속마음을 드러내는 대신. 예의 바름을 우선시하는 사람들도 있다. 예의 바름은 '방어적'이기도 하다. 
  • 솔직해짐으로써 타인의 비난을 감수할 것인가, 아니면 하고 싶은 말을 억누르면서 스스로를 미워할 것인가. 가급적이면 전자였으면 좋겠다. 
  • '내가 붙들고 있는 것을 언제 놓을 것인가'의 문제는 어찌 보면 우리가 어른의 인생을 살아가면서 부딪히는 가장 어려운 문제다.
  •  에세이는 저자의 연한 속살을 적나라하게 드러내는 자비 없는 장르의 글이다. 솔직함을 가장한 자기 포장인지, 담백하게 있는 그대로의 생각을 자유롭게 표현했는지는 글의 행간에서 모두 고스란히 드러나 독자에게 전달된다.
  • '자, 이제 이쯤에서 끝내야지'라고 마음의 결정을 내리는 것, 의식해서 그 사람 이야기를 하지 않고 그 사람에 대해 생각하지 않으려고 하는 것, 일에 몰두하거나 새롭게 집중할 수 있는 무언가를 찾는 것 등 스스로에게 과제를 주면서 이번 사랑이 끝났음을 받아들이기로 한다. 나는 이것을 '연애의 뒤처리'라고 말한다. 
  • 사실 진심으로 반가운 건 첫 재회의 순간뿐이다. 막상 우연이 아닌 인위적인 방법으로 다시 만나야 한다면 부담스럽고 재미없을 것 같다.  현재보다 과거를 공유해야 하는데 거기엔 대화의 한계가 있다. 과거 시절 즐거웠던 에피소드를 하나둘 끄집어내고, 그 시절에 알고 지낸 공통 지인들에 대한 근황을 공유한다. 대화 소재는 머지않아 바닥나기 쉽다. 그렇다고 현재의 생활을 공유하기엔 그만큼 서로에게 이젠 관심이 없거나 공통분모가 없다. 
  • 인간관계만큼은 영혼 없이 관리하고 싶지 않다. 형식적으로 부피만 커져가는 친분과 인맥은 삶을 성가시고 산만하게 할 뿐이다. 
  • 나의 자의식에 헛구역질이 났다. 
  • 어쩌면 그 모든 과거의 인연은, 차라리 다시 만나지 않는 것이 가장 아름다운지도 모르겠다. 
  • 모두가 같은 종류의 고통을 겪었기에 형식적인 위로는 필요가 없었다. 말로 표현하지 않아도 절로 이해하고 이해받고 있다고 실감했다. 
  • 밤늦게 은은한 스탠드 조명만 켜놓은 책상 앞에 앉아 글을 쓴다. 노트북컴퓨터 옆에는 따끈한 커피를 담은 머그잔이 놓여 있다. 한껏 집중하며 글을 쓰다가 주간에 잠시 머리를 식힐 때, 두 다리를 책상 위로 뻗고 담배 한 모금을 깊게 빤 뒤 후우, 하고 연기를 길게 내뿜을 수 있다면 얼마나 좋을까. 혹은 책 원고를 마침내 완성하고서 피우는 담배 한 모금은 또 얼마나 맛이 깊고 달까. 그러나 현실의 나는 늦은 밤이나 새벽은커녕, 햇살이 비추는 아침 아홉 시부터 시간에 쫒겨 바지런을 떨어가며 글을 쓴다. 화장실 갈 때를 빼놓고는 자세 한번 흩트리지 않고, 딴짓 한번 하지 않고 오르지 원고 작업만 한다. 그리고 노트북컴퓨터 옆에는 비타민c 한 포와 당근 주스가 놓여 있다. 이게 사는 건가.
--아직 읽는 중--

책을 읽다 보면 이전 특정 상황이나 인관관계에서 느꼈던 정리되지 않은 감정들 꼭 짚어 그 당시의 내 감정을 직접 겪은 것 마냥 풀어진 문구를 읽게 된다.
그 때의 시원함은 이루말로 표현할 수 없이 시원하다.


반응형
반응형


어제 목요일(1011) Deview 1일차에 참여하고 왔는데요


세션들 들으며 정리했던 내용 정리겸 포스팅


[세션 1 - Snow이상민 / 웹 개발자가 한달만에 앱 출시하기]

발표자료 : https://www.slideshare.net/deview/121react-native

내 별점 : ★★ (5개만점기준)


예상 발표  내용 : 웹 개발자가 앱을 출시하며 기존에 겪지 못했던 문제들을 어떻게 해결했는지, 어떤 부분이 달랐는지, 일정관리 부분

실제 발표 내용 : React Native 소개 및 사용시 주의사항

느낀점 : 일단 발표내용에 비해 제목이 너무 과하게 선정되지 않았나 하는 생각이 들었다. 

또한 기대했던 내용과는 다른 너무 React Native에 대한 내용이 주를 이뤘다. 발표 자체도 그냥 대본을 읽으시는느낌ㅠ

해당 발표자는 웹개발(프론트/백엔드)개발 경험은 십년을 훌쩍 넘은 분이셨고 '실제 첫 앱 개발이냐'는 질문에

그동안 공부는해왔다라고 말씀을 하셨음....실제 앱개발이 전혀없는 웹개발자 기준 AOS/IOS 앱을 1달만에 출시한다는건 약간 터무니 없어보인다?는 느낌이 들었음.



[세션 2 - 언체인(라인 블록체인 자회사) 대표 이홍규 / 서비스 오리엔티드 블록체인을 위한 스케일링 문제 해결]

발표자료 : https://www.slideshare.net/deview/132deview2018

내 별점 : ★★ (5개만점기준)


예상 발표 내용 : 블록체인을 서비스에 어떻게 녹였는지, 실제 앱에서 어떻게 동작하고 있는지

실제 발표 내용 : 블록체인 관련 용어 및 알고리즘에 대한 기본 개념 설명

느낀점 : 실제 너무 주제와 동떨어진 내용으로 전반적으로 사람들이 흥미를 느끼지 못하고 집중하지 못하는 모습이 많이 보였음(나포함...)



[세션3 - Naver 박재성 / Javascript 배틀그라운드로부터 살아남기]

발표자료 : https://www.slideshare.net/deview/123javascript

내 별점 : ★★★★★ (5개만점기준)


느낀점 : 요즈음 FE의 동향에 대해 굉장히 잘 설명해주셨음. 실제 FE쪽에 많은 경험이 있다는게 발표에서 느껴지는 발표였음

결론 : 수많은 FE기술에 집착하기보단 그때그때 필요한 기술들에 대한 관심과 학습



[세션4 - NBP 이덕현 / 네이버에서 사용되는 여러가지 Data Platform, 그리고 MongoDB ] 

내 별점 : ★★★☆ (5개만점기준)


느낀점 : 전반적인 내용은 MongoDB와 MongoDB사용시 주의사항

실제 발표자분은 개발자가 아닌 DBA분. MongoDB를 사용하고 있는 분들은 많은 도움이 되셨을 것 같다.



[세션5 - Naver 이형욱 / 웹 성능 최적화에 따른 브라우저의 모든 것 ]

발표자료 : https://www.slideshare.net/deview/125-119068291

내 별점 : ★★★★☆ (5개만점기준)


느낀점 : 브라우저 내부 동작 원리에 대해 잘 설명한 발표로 내용적인 측면도 꽤나 심도있게 잘 설명해주셨다.

웹 개발자라면 한 번 정도 자료를 보는 것을 추천



별점은 지극히 제 기준 위주입니다ㅎㅎ

전반적으로 내용에 비해 사람들을 끌여들이기 위해 제목을 자극적으로 뽑은 세션들이 꽤나 있었던 것 같습니다.

너무 과한 주제 선정은 너무 과한 기대를 가지게 하는 것 같습니다. 


이상 포스팅 끝~~나도 언젠간~

반응형
반응형


MAC 재시작 했을 때


자꾸 전에 작업하다가 자동 저장 된 파일이 떠서 귀찮은 경우가 있다.


이때 불필요하게 자동저장된 데이터라면 다음 경로로 가서 삭제해주도록 한다.


PowerPower이외에도 Microsoft제품들의 자동저장된 파일의 경로이다.


Finder "/Users/< username >/Library/Containers/com.microsoft.*


해당 경로 "/Users/< username >/Library/Containers/"로 가보면 다음의 microsoft폴더들을 볼 수 있다.


Powerpoint의 경우 

"/Users/< username >/Library/Containers/com.microsoft.Powerpoint/Data/Library/Preferences/AutoRecovery"


에 가보면 지긋지긋하게 귀찮게 굴었던 자동저장된 파일들이 있는 것을 볼 수 있다. (_autorecover 파일)


시원하게 날려주자~안녕~



반응형
반응형

카산드라 Connection Pooling에 따른 요청수와 요청 처리방법

'카산드라 클러스터 노드수가 많아지면 request처리할 있는 양이 얼마나 많아질까?' 라는 궁금증에서 시작

API서버에서 어떻게 Connection Pool이 설정되어 있고 설정에 따라 카산드라 클러스터 노드(node)당 얼마나 처리할 수 있는지 알아보자

(단순히 datastax문서의 내용에만 의지한 것으로 실제 서비스에서는 Network I/O나 다른 요인들에 의해 영향을 받을 수 있음을 유의하자!!!)

How managed node contactPoints?

// (1)
//ContactPoints 하나라도 존재해야함!!!
Assert.isTrue(StringUtils.hasText(contactPoints), "At least one server is required");

public Builder addContactPoints(String... addresses) {
    for (String address : addresses)
        addContactPoint(address);  (2)
    return this;
}

(3)
public Builder addContactPoint(String address) {
    // We explicitly check for nulls because InetAdress.getByName() will happily
    // accept it and use localhost (while a null here almost likely mean a user error,
    // not "connect to localhost")
    if (address == null)
        throw new NullPointerException();
    try {
        addContactPoints(InetAddress.getAllByName(address)); (4)
        return this;
    } catch (UnknownHostException e) {
        throw new IllegalArgumentException("Failed to add contact point: " + address, e);
    }
}

(5) 
public Builder addContactPoints(InetAddress... addresses) {
    Collections.addAll(this.rawAddresses, addresses);
    return this;
}

(6)
contactpoints는 배열로 관리됨
private final List<InetAddress> rawAddresses = new ArrayList<InetAddress>();

How selected node when API server requests

RounRobinPolicy : 라운드로빈방식에 대해서는 따로 설명하지 않겠다. (단순 동일하게 각 노드에게 돌아가면서 요청하는 방식)

스크린샷 2018-09-13 오전 9.32.04.png

Cassandra 버전 별 허용 Request수

Cassandra versions 1.2 and 2.0 allow the clients to send up to 128 requests without waiting for a response per connection.
Higher versions of Cassandra ( that is 2.1 or greater) allow clients to send up to 32768 requests without waiting for a response.
단순히 이 계산식으로 계산을 했을 때
한 노드 당 14억(1415577600)정도의 요청을 처리 할 수 있음.
http://datastax.github.io/nodejs-driver/features/connection-pooling/
스크린샷 2018-09-13 오전 9.25.46.png


Cassandra 커넥션 맺는 flow 및 ProtocolVersion에 따른 차이

참고 : https://docs.datastax.com/en/developer/java-driver/3.6/manual/pooling/


참고 : https://docs.datastax.com/en/developer/java-driver/3.6/manual/native_protocol/



ContactPoints는 클러스터 모든 서버 목록을 적어줘야하나???

결론을 먼저 말하자면 '그렇지 않다'이다!!!

실질적으로 어플리케이션이 로드될 때 카산드라 드라이버는 컨택포인트에 적어진 노드 하나에 접근하게 되고 

그 노드로부터 실제 클러스터의 노드 정보등을 받아와 메모리상에 메타정보로 관리하게 된다.

따라서 클러스터가 10대로 구성되어 있더라도 ContactPoints에는 2~3대만 기입해줘도 문제가 없다.

다음의 내용을 참고하자.

Contact points setting is a list of one or many node address. When creating a Cluster instance at client side, the driver tries to connect to the nodes specified in the "contact points" in order. If it fails to connect to the first node, try the next ... As long as one node is successfully connected, it does not try to connect the other nodes anymore.

Why it is not necessary to connect to all the contact points is because, each node contains the metadata of all the other nodes, meaning as long as one is connected, the driver could get infomation of all the nodes in the cluster. The driver will then use the metadata of the entire cluster got from the connected node to create the connection pool. This also means, it is not necessary to set address of all your nodes to the contact points setting. The best practice is to set the nodes which responds the fastest to the client as contact points.


자세한 내용이 궁금하다면 다음을 참고하자.


참고 : https://teddyma.gitbooks.io/learncassandra/content/client/which_node_to_connect.html  (Which Node to Connect)




반응형
반응형


Spark dataframe(스파크 데이터프레임)으로 작업 중 dataframe의 null값을 특정값으로 바꾸고 싶은 경우가 있다.


이 때 주의해야할 점은 dataframe의 컬럼의 자료형 타입에 맞게끔 변환해줘야 정상적으로 replace된다.



다음과 같은 데이터프레임(dataframe)이 있을 때 "bid_i"의 값을 0으로 변경하려고 다음을 실행


val result_df_q_new = result_df_q.na.fill(0, Seq("bid_i"))


위와 같은 명령을 수행하고 확인을 해도 정상적으로 null값이 0으로 변경되지 않은 걸 확인할 수 있었다.


원인은 bid_i의 자료형 타입에 맞지않게 변경하려했기 때문이다.



위에서 보듯이 "bid_i"의 자료형 타입은 string인데 0으로 변경(na.fill메서드를 하려고 하니 정상적으로 변환되지 않았던 것이다. 

(처리 도중 딱히 에러메세지가 없었다...)


val result_df_q_new = result_df_q.na.fill("0", Seq("bid_i"))


0을 string형(큰따옴표)를 씌워서 명령어를 주니 정상적으로 변경되는 것을 확인할 수 있었다.


데이터프레임(dataframe) 값을 na.fill을 통해 변경할 때는 자료형타입을 잘 확인하도록 하자!


반응형
반응형

[ Java8 ] Stream Collectors toMap 사용시 Duplicate Key Error


DB로부터 데이터를 가져와 List에 담고 List에 담긴 데이터를 MAP에 담아 처리하는 작업이다.


List to Map 시 Key 값이 중복일 경우 Duplicate Key에러 발생

2018:08:08 19:47:49.947 ERROR --- [http-nio-80-exec-24] o.a.c.c.C.[.[.[.[dispatcherServlet] : Servlet.service() for servlet [dispatcherServlet] in context with path [] threw exception [Request processing failed; nested exception is java.util.concurrent.CompletionException: java.lang.IllegalStateException: Duplicate key 31356962-6f5b-4280-9beb-f48d4c437695] with root cause

java.lang.IllegalStateException: Duplicate key 31356962-6f5b-4280-9beb-f48d4c437695

        at java.util.stream.Collectors.lambda$throwingMerger$0(Collectors.java:133)

        at java.util.HashMap.merge(HashMap.java:1254)



[ 에러가 발생했던 코드 ]

CompletableFuture<List<Partner>> matchedList = cookieMatchingRepository.getMatchedPartnerUserIdByBid(bid);
Map<String, String> matchedPartnerMap =
matchedList.get().stream().collect(Collectors.toMap(Partner::getPartnerId, Partner::getPartnerUserId));


[ 동일한 KEY값이 들어와도 처음 KEY-VALUE 값으로 처리하는 코드 (노란 부분이 바뀜) ]

CompletableFuture<List<Partner>> matchedList = cookieMatchingRepository.getMatchedPartnerUserIdByBid(bid);
Map<String, String> matchedPartnerMap = matchedList.get().stream()
.collect(Collectors.toMap(Partner::getPartnerId, Partner::getPartnerUserId, (p1, p2) -> p1));



반응형

+ Recent posts