XML(eXtensible Markup Language)은 W3C에서 개발된, 다른 특수한 목적을 갖는 마크업 언어를 만드는데 사용하도록 권장하는 다목적 마크업 언어이다.
- 또 다른 마크업 언어인 HTML은 모든 사용자가 공유하는 미리 정의된 태그 집합으로 제한된다.
- XML은 데이터 및 해당 데이터의 구조를 설명하는데 필요한 태그를 만들 수 있다.
동물에 관련하여 XML태그 사용
<Animal>
<Dog>
<NAME>
</NAME>
<AGE>
</AGE>
</Dog>
<Cat>
<NAME>
</NAME>
<AGE>
</AGE>
</Cat>
</Animal>
XML은 플랫폼에 독립적이기 때문에 XML을 구축하기 위해 구축된 모든 프로그램이 하드웨어 또는 운영 체제에 관계없이 XML데이터를 읽고 처리할 수 있다.
DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
DocumentBuilder builder = factory.newDocumentBuilder();
Document document = builder.newDocument();
document.setXmlStandalone(true); // standalone="no" 제거
Element createElement(String tagName)
Element 객체를 생성한다.
Attr createAttribute(String name)
Attribute 객체를 생성한다.
Text createTextNode(data)
Text 객체를 생성
Comment createComment(data)
Comment 객체를 생성
appendChild(노드명)
노드명을 자식노드로 추가
setOutputProperty("설정할 것" , "설정할 내용")
출력할 때 추가적인 옵션을 설정할 수 있다.
package ex02_writer;
import java.io.File;
import java.util.Arrays;
import java.util.List;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.transform.Source;
import javax.xml.transform.Transformer;
import javax.xml.transform.TransformerFactory;
import javax.xml.transform.dom.DOMSource;
import javax.xml.transform.stream.StreamResult;
import org.w3c.dom.Document;
import org.w3c.dom.Element;
public class XMLWriter {
public static void main(String[] args) {
try {
// Document 생성(문서 생성)
DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
DocumentBuilder builder = factory.newDocumentBuilder();
Document document = builder.newDocument();
document.setXmlStandalone(true); // standalone="no" 제거
// Document에 products 태그 추가
Element products = document.createElement("products");
document.appendChild(products);
List<String> product1 = Arrays.asList("100", "새우깡", "1500");
List<String> product2 = Arrays.asList("101", "양파링", "2000");
List<String> product3 = Arrays.asList("102", "홈런볼", "3000");
List<List<String>> list = Arrays.asList(product1, product2, product3);
for(List<String> line : list) {
// 태그 생성
Element product = document.createElement("product");
Element number = document.createElement("number");
number.setTextContent(line.get(0)); // 0번째 배열 애들을 다 데려옴
Element name = document.createElement("name");
name.setTextContent(line.get(1)); // 1번째 배열 애들을 다 데려옴
Element price = document.createElement("price");
price.setTextContent(line.get(2)); // 2번째 배열 애들을 다 데려옴
// 태그 배치
products.appendChild(product); // 변경
product.appendChild(number);
product.appendChild(name);
product.appendChild(price);
}
// XML 생성
TransformerFactory transformerFactory = TransformerFactory.newInstance();
Transformer transformer = transformerFactory.newTransformer();
transformer.setOutputProperty("encoding", "UTF-8"); // setOutputProperty : 출력형태 만들 때 사용
transformer.setOutputProperty("indent", "yes"); // indent : 들여쓰기
transformer.setOutputProperty("doctype-public", "yes"); // document.setXmlStandalone(true); 하면 개행이 안 되기 때문에 추가
Source source = new DOMSource(document);
File file = new File("C:\\storage", "product.xml");
StreamResult result = new StreamResult(file);
transformer.transform(source, result);
} catch (Exception e) {
e.printStackTrace();
}
}
}
<products>
<product>
<number>100</number>
<name>새우깡</name>
<price>1500</price>
</product>
<product>
<number>101</number>
<name>양파링</name>
<price>2000</price>
</product>
<product>
<number>102</number>
<name>홈런볼</name>
<price>3000</price>
</product>
</products>
우선 클래스를 따로 생성해서 필드와 Getter/Setter를 설정해주고,
public class Product {
private String number;
private String name;
private int price;
public Product() {
// TODO Auto-generated constructor stub
}
public Product(String number, String name, int price) {
super();
this.number = number;
this.name = name;
this.price = price;
}
public String getNumber() {
return number;
}
public void setNumber(String number) {
this.number = number;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getPrice() {
return price;
}
public void setPrice(int price) {
this.price = price;
}
@Override
public String toString() {
return "Product [number=" + number + ", name=" + name + ", price=" + price + "]";
}
}
메인메소드를 작성 해준다.
import java.io.File;
import java.util.ArrayList;
import java.util.List;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
public class XMLReader {
public static void main(String[] args) {
try {
DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
DocumentBuilder builder = factory.newDocumentBuilder();
File file = new File("C:\\storage", "product.xml");
Document document = builder.parse(file); // product.xml 파싱(분석)
// 최상위 요소(root)
Element root = document.getDocumentElement();
System.out.println("최상위 요소 : " + root.getNodeName());
List<Product> products = new ArrayList<Product>();
// 최상위 요소의 자식 노드들
NodeList nodeList = root.getChildNodes(); // 자식노드들 가져오기
for(int i = 0; i < nodeList.getLength(); i++) {
Node node = nodeList.item(i); // 줄바꿈(#text)과 <product> 태그로 구성 노드리스트 안에 들어있는 노드들.
// System.out.println(node.getNodeName()); //#text product #text product #text product #text
if(node.getNodeType() == Node.ELEMENT_NODE) { // ELEMENT_NODE : Element요소인지 확인하는 것 (줄바꿈(#text) 뺴기위함)
// System.out.println(node.getNodeName()); // <product> 태그의 자식노드(줄바꿈 (#text), <number>, <name>, <price> 태그)
NodeList nodeList2 = node.getChildNodes();
Product product = new Product();
for(int j = 0; j < nodeList2.getLength(); j++) {
Node node2 = nodeList2.item(j);
if(node2.getNodeType() == Node.ELEMENT_NODE) {
switch(node2.getNodeName()) {
case "number" : product.setNumber(node2.getTextContent()); break;
case "name" : product.setName(node2.getTextContent()); break;
case "price" : product.setPrice(Integer.parseInt(node2.getTextContent())); break;
}
}
}
products.add(product);
}
//textContent = 태그와 태그사이의 값을 가리키는 말
// 줄바끔도 Node로 인식된다.
}
// ArrayList 확인
for(Product product : products) {
System.out.println(product);
}
} catch (Exception e) {
e.printStackTrace();
}
}
}