지식메모/JAVA

 

기본 코드는 이 링크를 참고하였습니다.

https://javaslave.tistory.com/78

 

POI Library를 이용한 Excel Read

Apache POI Grid 형태의 데이터를 핸들링 하는 화면에는 보통 '엑셀다운로드', '엑셀업로드' 버튼이 존재한다. 이를 구현하기 위해서 Apache에서 제공하는 POI 라이브러리를 이용하는 방법을 알아보도록 하자. Jav..

javaslave.tistory.com

 

POI 버전은 3.11을 사용하였습니다. (최신 poi 4점대 버전에서는 코드가 동작하지 않습니다)

poi 3.11 라이브러리 파일

lib (2).zip
7.51MB
lib.zip
3.21MB

용량 제한으로 압축파일 2개로 나뉘어 첨부함

 

사용 용도 

엑셀 내용( 확장자 xlsx 필수)
account.xlsx
0.01MB

위와 같은 엑셀 내용에서 각 열 별로 데이터를 긁어와 각 ArrayList에 저장함

로그인시

ID에는 ArrayList1.get(0)

암호에는 ArrayList2.get(0) 

이런 식을 1:1 매칭해서 로그인에 활용하는 단순 용도

총 6개의 ArrayList  선언 (액셀에 총 6개의 열이 있기 때문)

 

스위치 문에서 각 열마다 1개의 ArrayList에 값을 넣음

발생하는 문제점

첫 열의 개수에 따라 나머지 열의 개수가 결정됨

첫 열이 10개고 나머지 열이 20개,16개 등등 제 각기라면 첫 열 기준으로 모두 10개의 데이터만 가져오게 되는 문제가 존재함

 

전체 코드

package poi;

import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;

import org.apache.poi.xssf.usermodel.XSSFCell;
import org.apache.poi.xssf.usermodel.XSSFRow;
import org.apache.poi.xssf.usermodel.XSSFSheet;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;

public class POIReader {
    public static List<String> account1 = new ArrayList<String>();
    public static List<String> account2= new ArrayList<String>();
    public static List<String> account3 = new ArrayList<String>();
    public static List<String> account4 = new ArrayList<String>();
    public static List<String> account5 = new ArrayList<String>();
    public static List<String> account6 = new ArrayList<String>();
    
   /**
    * XLSX 파일을 분석하여 List<poi> 객체로 반환
    * @param filePath
 * @return 
    * @return
    */
   public static void xlsxTopoiList(String filePath) {
       // 반환할 객체를 생성
       FileInputStream fis = null;
       XSSFWorkbook  workbook = null;
       
       try {
           
           fis= new FileInputStream(filePath);
           // XSSFWorkbook은 엑셀파일 전체 내용을 담고 있는 객체
           workbook = new XSSFWorkbook (fis);
           
           // 탐색에 사용할 Sheet, Row, Cell 객체
           XSSFSheet curSheet;
           XSSFRow   curRow;
           XSSFCell  curCell;
//           poiList vo;
           
           // Sheet 탐색 for문
           for(int sheetIndex = 0 ; sheetIndex < workbook.getNumberOfSheets(); sheetIndex++) {
               // 현재 Sheet 반환
               curSheet = workbook.getSheetAt(sheetIndex);
               
               // row 탐색 for문
               for(int rowIndex=0; rowIndex < curSheet.getPhysicalNumberOfRows(); rowIndex++) {
                   // row 0은 헤더정보이기 때문에 무시
                   if(rowIndex != 0) {
                       // 현재 row 반환
                       curRow = curSheet.getRow(rowIndex);
//                       vo = new poiList();
                       String value;
                           // row의 첫번째 cell값이 비어있지 않은 경우 만 cell탐색
                       System.out.println("---"+curRow.getCell(0));
                       if(curRow.getCell(0) != null){ // 첫번째열 모자를 때 구분
                    	   if(!"".equals(curRow.getCell(0).getStringCellValue())) {
                               
                               // cell 탐색 for 문
                               for(int cellIndex=0;cellIndex<curRow.getPhysicalNumberOfCells(); cellIndex++) {
                                   curCell = curRow.getCell(cellIndex);
                                   
                                   if(true) {
                                       value = "";
                                       // cell 스타일이 다르더라도 String으로 반환 받음
                                       if(curCell != null){ //각 열의 목록 길이에 따라 분기
                                    	   switch (curCell.getCellType()){
                                           case XSSFCell.CELL_TYPE_FORMULA:
                                               value = curCell.getCellFormula();
                                               break;
                                           case XSSFCell.CELL_TYPE_NUMERIC:
                                               value = curCell.getNumericCellValue()+"";
                                               break;
                                           case XSSFCell.CELL_TYPE_STRING:
                                               value = curCell.getStringCellValue()+"";
                                               break;
                                           case XSSFCell.CELL_TYPE_BLANK:
                                               value = curCell.getBooleanCellValue()+"";
                                               break;
                                           case XSSFCell.CELL_TYPE_ERROR:
                                               value = curCell.getErrorCellValue()+"";
                                               break;
                                           default:
                                               value = new String();
                                               break;
                                           }
                                       }
                                       switch (cellIndex) {
                                       case 0: // name
                                    	   account1.add(rowIndex-1, value);
                                           break;
                                           
                                       case 1: // 암호                                	   
                                    	   account2.add(rowIndex-1, value);
                                           break;
                                           
                                       case 2: // 여기서 하나씩 분류
                                    	   account3.add(rowIndex-1, value);
                                           break;
           
                                       case 3: // 여기서 하나씩 분류
                                    	   account4.add(rowIndex-1, value);
                                           break;
                                           
                                       case 4: // 여기서 하나씩 분류
                                    	   account5.add(rowIndex-1, value);
                                           break;
                                           
                                       case 5: // 여기서 하나씩 분류
                                    	   account6.add(rowIndex-1, value);
                                           break;
                                       default:
                                           break;
                                       }
                                   }
                               }
                           }
                       }
                       
                   }
               }
           }
       } catch (FileNotFoundException e) {
           // TODO Auto-generated catch block
           e.printStackTrace();
       } catch (IOException e) {
           // TODO Auto-generated catch block
           e.printStackTrace();
           
       } finally {
           try {
               // 사용한 자원은 finally에서 해제
               if( workbook!= null) 
            	   workbook.close();
               if( fis!= null) fis.close();
               
           } catch (IOException e) {
               // TODO Auto-generated catch block
               e.printStackTrace();
           }
       }
   }
}

 

 

String 배열을 사용해서 콤보박스에 값들을 보여줬었는데

ArrayList를 사용해서 콤보박스에 보여주고 싶었따.

스트링 배열은 String[] account1 = { id,id1,id2}

이런식으로 콤마로 이루어진 값이었는데 ArrayList는 배열마다 각 값을 가지고 있기 때문에 나중에 관리하기 편할 것 같았다.

기존 String 배열(account1)을 콤보박스에 넣었을 때 코드

JComboBox<?> comboBox = new JComboBox<Object>(account1);

ArrayList(account1)를 콤보박스에 넣을 때 코드

JComboBox<?> comboBox = new JComboBox(account1.toArray(new String[account1.size()]));

이렇게 하면 account1 배열의 사이즈만큼 알아서 콤보박스에 값이 노출되었다

참고링크


http://blog.naver.com/battledocho/220035925900



이런 Json배열 하나에 여러개의 Json이 있다고 가정했을 때


Json 값마다 있는 idx,link,description 키값을 사용해 데이터를 저장해보았다.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
String eventArray = null//Json Array를 String으로 저장하기 위한 변수 선언
try {
    eventArray = loadHtml(); //loadHtml()는 Json Array를 파싱해서 String으로 가져오는 함수라 가정
catch (InterruptedException e) {
    e.printStackTrace();
}
System.out.println("결과물 : " + eventArray);
try {
    JSONArray array = new JSONArray(eventArray); //JSONArray형식으로 파싱하기 위해 새로 선언해주며 eventArray를 집어 넣어준다.
    list_cnt = array.length(); //Json 배열 내 JSON 데이터 개수를 가져옴
 
    //key의 value를 가져와 저장하기 위한 배열을 생성한다
    getDescription = new String[list_cnt]; //decription 저장용
    getLink = new String[list_cnt]; //link 저장용
    getImageUrl = new String[list_cnt]; //imageUrl 저장용
 
    for (int i = 0; i < list_cnt; i++) { //JSONArray 내 json 개수만큼 for문 동작
 
        JSONObject jsonObject = array.getJSONObject(i); //i번째 Json데이터를 가져옴
        getDescription[i] = jsonObject.getString("description");  //descripton 값을 배열에 저장
        getLink[i] = jsonObject.getString("link");  //link 값을 배열에 저장
        getImageUrl[i] = jsonObject.getString("imageUrl");  //imageurl 값을 배열에 저장
        Log.i("JSON Object", jsonObject + "");
        Log.i("JsonParsing", getDescription[i] + "," + getLink[i] + "," + getImageUrl[i]);
 
    }
cs


Log로 찍어보면

JsonObject의 로그

I/JSON Object: {"idx":15858,"imageUrl":"http:\/\/img.cgv.co.kr\/Event\/Event\/2017\/0330\/some_240x200_01.jpg","link":".\/detail-view.aspx?idx=15858&menu=2","description":"<어느날>1+1 예매 이벤트"}


파싱해낸 데이터 description, link, imageUrl 순으로 파싱이 된 걸 볼 수 있다.

I/JsonParsing: <어느날>1+1 예매 이벤트,./detail-view.aspx?idx=15858&menu=2,http://img.cgv.co.kr/Event/Event/2017/0330/some_240x200_01.jpg


배열에 잘 들어갔는지 description을 예로 확인을 해보면

for(int i=0;i<description.length;i++){
System.out.println("배열값 : "+description[i]);
}


I/System.out: 배열값 : <시간위의 집>스타★라이브톡

I/System.out: 배열값 : <보통사람>1+1 예매권 2차 이벤트

I/System.out: 배열값 : <로즈> 기대평 이벤트

I/System.out: 배열값 : <공각기동대:고스트 인 더 쉘>예매 경품 이벤트


description 값만 따로 배열에 잘 들어가있음을 확인할 수 있다.


이제 파싱해낸 값으로 다양한 곳에 쓸 수 있다.



  1. 2018.01.22 23:10

    비밀댓글입니다

subString 함수사용

subString(시작위치,끝위치);

예를 들어 애국가에서 

하느님이 ~ 우리나라만세 사이에 텍스트를 추출하고 싶다면

String song = "하느님이 보우하사 우리나라만세";

int start = song.indexOf("하느님이"); //하느님이 위치 추출

int end = song.indexOf("우리나라만세"); //우리나라만세 추출

String parseText = song.subString(start,end);

이런 방법도 있다





또 이상한 에러가 발생.. 이클립스가 이상한건가..

에러 내용은 이러하다

java.lang.SecurityException: class "org.hamcrest.Matchers"'s signer information does not match signer information of other classes in the same package

at java.lang.ClassLoader.checkCerts(ClassLoader.java:895)

at java.lang.ClassLoader.preDefineClass(ClassLoader.java:665)

at java.lang.ClassLoader.defineClass(ClassLoader.java:758)

at java.security.SecureClassLoader.defineClass(SecureClassLoader.java:142)

at java.net.URLClassLoader.defineClass(URLClassLoader.java:455)

at java.net.URLClassLoader.access$100(URLClassLoader.java:73)

at java.net.URLClassLoader$1.run(URLClassLoader.java:367)

at java.net.URLClassLoader$1.run(URLClassLoader.java:361)

at java.security.AccessController.doPrivileged(Native Method)

at java.net.URLClassLoader.findClass(URLClassLoader.java:360)

at java.lang.ClassLoader.loadClass(ClassLoader.java:424)

at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:308)

at java.lang.ClassLoader.loadClass(ClassLoader.java:357)

at NaverAPITest.NAPITest.test.test(test.java:35)

at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)

at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)

at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)

at java.lang.reflect.Method.invoke(Method.java:483)

at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:50)

at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)

at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:47)

at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:17)

at org.junit.internal.runners.statements.RunBefores.evaluate(RunBefores.java:26)

at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:325)

at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:78)

at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:57)

at org.junit.runners.ParentRunner$3.run(ParentRunner.java:290)

at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:71)

at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:288)

at org.junit.runners.ParentRunner.access$000(ParentRunner.java:58)

at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:268)

at org.junit.runners.ParentRunner.run(ParentRunner.java:363)

at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:86)

at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38)

at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:459)

at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:678)

at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:382)

at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:192)



찾아보니 라이브러리 중복으로 인해 발생된다고 한다.

Junit의 라이브러리가 문제라는데..

org.hamcrest.Matchers

아무튼 JUnit4 저걸 통째로 remove하여 제거하였다.


그리고 다시 실행했더니 웬 에러???

pom.xml을 가봤더니 Junit 3.8.1 로 되어있었다. 


그래서 저걸 지워버리고

<dependency>

<groupId>junit</groupId>

<artifactId>junit</artifactId>

<version>4.12</version>

</dependency>

이걸 추가해주었더니 에러가 사라졌다!

이제 실행하니 잘되었따







자바에서 프로그램을 만든 뒤 프레임바 아이콘을 바꾸고 싶었다.


바로 요놈을 바꿔주고 싶었다.





그래서 프로젝트 내 이미지 파일을 복사한 뒤 아이콘을 변경하기로 했다.




icon 폴더 생성 후 p.png 파일을 넣었다.


그런다음


ImageIcon img = new ImageIcon("icon/p.png");

        win.setIconImage(img.getImage());



이렇게 코드를 넣어주고 실행하면 변경됐으나 


 Runnable JAR 즉 실행가능한 JAR 파일로 생성하여 실행하면 변경되지가 않았다.


왜 jar 파일로만 생성하면 안되는 걸까해서 찾아본 결과 이미지가 있는 폴더도 같이 묶어주어야 했다.




먼저 프로젝트 우클릭 > properties 에 들어간 뒤 Java Build Path 에 들어간다.


Source 탭에서 Add Folder 를 선택한다.






그런다음 이미지가 있는 폴더를 체크해준다.

여기서는 icon 폴더





적용한 다음 저 위치의 경로를 추출하기 위해 다음 코드를 써준다.


1
2
3
4
 URL imageURL = 클래스명.class.getClassLoader().getResource("p.png");
 ImageIcon img = new ImageIcon(imageURL);
 JFrame객체.setIconImage(img.getImage());
 
cs



이렇게 해주면 프레임바 아이콘이 교체된다.

한번 이클립스에서 실행해보고 적용됐는지 확인해본다.





적용한 다음 프로젝트 우클릭 > Export > Java > Runnable JAR file 선택













Launch configuration 에서 실행될 클래스 지정해주고


Library Handling 에서 두번째 선택한 뒤 finish 해준다.


이유는 모르겠으나 두번째로 해야 적용이 되었다.








그리고 생성된 jar 파일을 실행해보고 아이콘이 바뀌었나 확인해본다.


그럼 어느 컴퓨터를 가도 아이콘은 적용되어 있을 것이다.














ImageIcon img = new ImageIcon("이미지경로");

해당프레임.setIconImage(img.getImage());

+ Recent posts