'XML'에 해당되는 글 5건

  1. 2009.09.29 XML 파일 읽기를 테스트해 보았다... (Count)
  2. 2009.08.11 DataSet 을 이용한 XML 다루기
  3. 2007.07.10 XML 기본 내용 (2)
  4. 2007.06.28 Web 2.0 Machine is using us 한국자막
  5. 2007.04.11 Five Ajax Anti Pattern
2009.09.29 14:09

XML 파일 읽기를 테스트해 보았다... (Count)

XML 파일 읽기를 테스트해 보았다...

C#에서 읽는 것과 같을거라 생각이 든다

1. 새로 프로젝트를 생성 한다.
2. 폼에 Label 하나를 추가 한다.(XML 읽어서 보여 주려고)
3. XML 파일을 추가한다.(프로젝트 이름에서 오른쪽 마우스 클릭> 추가 > 새항목)



4. 아래와 같은 화면에서 XML 파일을 선택하고 이름을 입력후 추가를 클릭 한다.



5. 생성된 XML에 아래와 같이 XML 데이트를 만든다.


6. using System.Xml; 를 추가해 준다.
7. Load 이벤트에 아래와 같이 코딩을 한다.

        private void XMLFrm_Load(object sender, EventArgs e)
        {
            DataSet ds = new DataSet(); //XML를 읽어 들일 DataSet 객체
            XmlDocument xd = new XmlDocument(); //XML 데이터를 담을 Document 객체(이 객체 때문에 using System.Xml 를 선언 한것임) 

            ds.ReadXml(@"\Program Files\TestPro\XMLFile1.xml");//XML를 읽기
            xd.LoadXml(ds.GetXml()); //XML 로드

            int datacnt = 0; //전체 데이터 갯 수
            string xmltxt; //XML 데이터를 출력을 위한
            string fTagName; //Tag Name를 저장 하기 위한

            fTagName = xd.FirstChild.ChildNodes.Item(0).Name; // XML 구조에 따라 틀리 수 있다

            datacnt = xd.GetElementsByTagName(fTagName).Count;

            xmltxt = "전체 데이터 수 : " + datacnt.ToString() + "\n";

            for (int i = 0; i < datacnt; i++)
            {
                for (int j = 0; j < xd.GetElementsByTagName(fTagName).Item(i).ChildNodes.Count; j++)
                {
                    xmltxt = xmltxt + xd.GetElementsByTagName(fTagName).Item(i).ChildNodes.Item(j).InnerText + "###";
                }

                xmltxt = xmltxt + "\n";
            }

//Tag Name을 알고 있을때는 아래와 같이 해도 된다.

            datacnt = xd.GetElementsByTagName("testdata").Count;

            xmltxt = xmltxt + "TagName 알고 있을때 " + "\n";
            xmltxt = xmltxt + "전체 데이터 수 : " + datacnt.ToString() + "\n";

            for (int i = 0; i < datacnt; i++)
            {
                xmltxt = xmltxt + xd.GetElementsByTagName("testtitle").Item(i).InnerText + "###";
                xmltxt = xmltxt + xd.GetElementsByTagName("testnumber").Item(i).InnerText + "###";
                xmltxt = xmltxt + xd.GetElementsByTagName("testimgpath").Item(i).InnerText + "###";

                xmltxt = xmltxt + "\n";
            }

            label1.Text = xmltxt;


        }




8. 빌드 하고 실행한다. (아래와 같은 결과를 확인 할 수 있다.)



신고
Trackback 0 Comment 0
2009.08.11 17:08

DataSet 을 이용한 XML 다루기

들어가면서...

C#에서 XML을 다루는 방법을 알아볼 예정이다. 뜬금없는 웬 XML 타령이냐고 따지고 들지 모르니, XML이 어떤 것이고 XML을 어떤 경우에 사용하는지 간단하게 알아보도록 하자. XML은 eXtensible Markup Language 의 약자이다. 단어의 뜻만 보자면 확장 가능한 데이터 기술 언어라는 것이다. 뭔소린지 아직 도통 글을 쓰는 필자도 감이 안온다. 그럼 XML을 정의하는 표준 문서를 열어보자. http://www.w3.org/XML/ 페이지를 열어보자..뜨앗..영어다 -_-; 그럼 소박하게 번역해보자. ISO 8879 국제표준 SGML에서 정의된 간단하고 아주 유연한 텍스트 형식이라고 한다. 그러니까 간단히 말하면 데이터 자체와 데이터의 포맷 형태를 동시에 공유할 수 있도록 해주는 차세대 정보 포맷이라는 말이다. 혹시 아직 말이 어렵다고 느끼는가? 그렇다면 간단하게 html에서 사용하는 tag와 같은 것을 사용자들이 정의하여서 그것들을 그룹화 해놓은 파일이라고 일단은 이해하고 넘어가도록 하자.

XML

XML은 단순하고 읽기 쉽고 표준이라는 3가지의 장점을 가진다. XML은 사용자들이 정의하는 데이터의 타입과 데이터의 값, 데이터의 표현을 가지기 때문에 단순하다는 장점을 가지며, 바이너리 형식이 아닌 텍스트형식의 포맷을 가지기 때문에 읽기 쉽다는 장점도 가지고 있지만, <nodedata>nodevalue</nodedata>와 같은 형식으로 데이터를 표현하기 때문에 데이터의 크기가 크고, 데이터가 크기 때문에 데이터의 전달이 오래 걸릴 수 있다는 단점 또한 같이 가진다. 여튼 XML은 표준이다. 표준으로서 가지는 장점은 다른 단점들을 모두 가릴 수는 없겠지만, 그래도 표준이기 때문에 많은 사람들이 지키고 그 사람들이 만드는 어플리케이션에서 사용할 것이다.

그럼 XML 이용형태에 대해서 3가지 정도를 알아보도록 하자. 먼저 웹 서비스의 데이터 전달이다. 웹 서비스에서 XML을 이용하여 데이터를 전달하는 부분은 나중에 웹 서비스에 대한 글을 적을 때 더 깊이 다루도록 하고 일단, 웹 서비스는 분산객체기술의 한 부분이라는 점만을 알고 넘어가자. 그리고 다음으로는 여러 가지 전자기기에서 사용이 된다. Home Auto 등으로 대변되는 우리의 미래 생활에서 동작되는 전자레인지와 같은 많은 전자제품들과의 데이터 통신에서도 사용할 수 있다. 마지막으로 간단한 DBMS와 같은 데이터 저장소로서의 역할이다.

자…이제 그럼 각설하고, C#에서 XML을 다루는 방법에 대해서 여러 가지를 알아볼 것인데, 오늘은 C#에서 XML을 가장 편하게 다룰 수 있는 방법인 DataSet을 통한 XML의 이용에 대해 알아보자.

DataSet을 이용한 XML 다루기

책상위의 몇 가지 객체에 관련한 데이터를 관리하는 XML을 하나 만들어 보도록 하자.

먼저 첫 Node는 펜이고, 가격은 200원이다.
다음 Node는 지우개이고, 가격은 300원이다.
XML 선언이 간단해 보이는가? 그게 XML의 최고의 장점이랜다..-_-;;;

위의 XML을 DataSet으로 가지고 오면 아래의 영역이 하나의 DataTable이 된다.

아래의 영역이 하나의 DataColumn이 된다.

아래의 영역이 하나의 DataRow가 된다.

VS2003에서 XML 파일을 열어보면 데이터셋과 유사하게 나오는 화면이 있어서 해당 부분이 XML을 DataSet으로 변환했을 때의 좋은 이미지인 것 같아 캡쳐해보았다.

자 그럼 이제 코드를 보도록 하자.

먼저 DataSet을 이용한 XML 다루기에서 키워드가 되는 2가지 함수는 ReadXml과 WriteXml이다.
ReadXml에 관련한 정보는
http://msdn.microsoft.com/library/default.asp?url=/library/en-us/cpref/html/frlrfsystemdatadatasetclassreadxmltopic2.asp
에서 자세하게 찾아볼 수 있으며,
WriteXml에 관련한 정보는
http://msdn.microsoft.com/library/default.asp?url=/library/en-us/cpref/html/frlrfsystemdatadatasetclasswritexmltopic.asp
에서 찾아볼 수 있다.

XML을 DataSet으로 읽기

DataSet ds = new DataSet();
ds.ReadXml(XML파일경로);

DataSet을 XML로 저장하기

ds.WriteXml(xmlFilePath);

전체소스

test.xml

<?xml version="1.0" standalone="yes"?>
<items>
<item name="pen">
<cost>203</cost>
</item>
<item name="eraser">
<cost>300</cost>
</item>
</items>

program.cs

using System;
using System.Data;
namespace testApp
{
class Program
{
static void Main(string[] args)
{
DataSet ds = new DataSet();
ds.ReadXml("test.xml");
for (int i = 0; i < ds.Tables[0].Rows.Count; i++)
{
if (ds.Tables[0].Rows[i]["name"].ToString().Equals("pen"))
{
ds.Tables[0].Rows[i]["cost"]=int.Parse(ds.Tables[0].Rows[i]["cost"].ToString())+1;
}
ds.WriteXml("test.xml");
}
ds.Dispose();
}
}
}

헌데 이 간단한 방법은 너무나 많은 규칙을 요구한다.
아래와 같은 XML 파일이 있다고 가정해보자.

위의 XML 파일을 보면, 한 Node에서 Attribute Name과 해당 Node의 하위 Node의 Name이 동일하다.
위 상황은 DataSet으로 만들었을때 DataColumn의 Name이 충돌이 날 수 있기 때문에
실제로 동작을 시켜보면

위와 같은 에러를 뿜으며 장렬히 산화한다.

글을 마치며

DataSet을 이용한 XML을 다루는 것은 그 코드가 간단하고 사용방법이 쉽다는 장점이 있지만, 해당 XML 문서내의 데이터가 DataSet과 거의 똑같은 구조를 유지해야한다는 치명적인 단점이 있다. 하지만, 이러한 단점을 보유하고서라도 그 사용법이 간단하다는 점에서 테스트 또는 일부 서비스에서 사용하는 것에는 절대 무리가 없다고 생각한다.
오늘은 간단하게 DataSet을 이용해서 XML을 다루는 방법을 알아보았으며,
추후 XmlWriter, XmlReader, XmlDocument등 다른 여러가지 XML을 다루는 방법에 대해 알아볼 것을 약속하며 이만 글을 줄일까 한다.
------------------------------------------------------------------------------------------------------
출처 : http://www.hoons.kr/Lecture/LectureView.aspx?BoardIdx=231&kind=26 


 * 주인장의 덧붙이는 말

 DataSet을 이용해서 XML 파일을 만들때 각각의 애트리뷰트와 엘리먼트를 표현하고자 할때에는 DataColumn의 ColumnMapping 속성을 이용하여 DataColumn의 속성을 지정할수 있다.

           DataColumn j_journal_data_Id = new DataColumn("journal_data_Id");
            j_journal_data_Id.ColumnMapping = MappingType.Hidden;

위의 코드는 컬럼 타입을 Hidden으로 지정하여 XML로 Export 할때 표현되지 않도록 한것이다.
Hidden 속성 외에도 Attribute, Element, SimpleText의 속성이 있다.

또한, 각 노드간의 부모-자식 관계를 표현하려면 DataTable간의 Relation을 이용해 표현할 수 있으며 각 테이블간의 관계를 나타낼 수 있는 ID 컬럼을 만들어 관계를 설정하면 된다.

저작자 표시 비영리 변경 금지
출처 : http://dailykim.tistory.com/20
신고
Trackback 0 Comment 0
2007.07.10 11:00

XML 기본 내용



Dom이란 객체 덩어리이다.

웹 페이지와 관련된 잡업을 쉽게 할 수 있도록 유용한 기능의 많은 객체를

만들어서 그 객체의 이름을 DOM이라고 했습니다. 이 DOM은 자바스크립트

와 객체를 사용하는 vbscript에서도 사용할 수 있습니다.2007-07-09 17:38:47 월요일

DOM은 브라우저 안에 있습니다. 그래서 가끔 브라우저 내장 객체라고 부르는

사람도 있습니다.

간단히 말해서 DOM이란 웹 문서를 작성할 때 자유롭게 불러서 사용할 수

있는 객체 모델입니다.

DOM(Document Object Model)

  • W3C's definition

    "The Document Object Model is a platform- and language-neutral interface that will alㅋlow programs and scripts to dynamically access and update the content, structure and style of documents.

    • dynamic access and update
      • XML/HTML 문서의 접근 및 수정 - 내용/구조/스타일 검색 및 수정
    • interface
      • 응용 프로그램(스크립트 포함) 인터페이스 : API - 각종 메소드 및 속성을 정의
      • 플랫폼 및 언어 중립적 : Java, JavaScript, ASP, ...
  • DOM의 역할
    • 문서내 객체(element)를 조작하기 위한 인터페이스(API)
      • 구조의 탐색 및 조작 : 각 요소와 속성에 대한 검색/질의가 가능, 추가/수정/삭제가 가능
      • 컨텐츠의 조작 : 문서 요소에서 text 등 컨텐츠의 검색/추가/수정/삭제가 가능
    • 대상 문서 : XML1.0 또는 HTML4.0, 기타 웹문서
  • DOM 사양
    • DOM level 1 : 1998.10 W3C Recommendation
    • DOM level 2 : 2000.11 W3C Recommendation
    • DOM level 3 : 2001.8 W3C Working Draft

DOM and XML Parser

  • Parser
    • XML 문서를 읽고 해석 : well-formed, valid 검사
    • 응용프로그램 개발시 파서 사용 이유
      • 세부적인 XML 문법으로부터 프로그램 격리
      • 파서가 메모리에 DOM 트리를 생성 : XML 문서트리와 일치

  • DOM 트리
    • 노드/객체의 종류
      • Document : 문서 객체, 최상위 노드
      • Element, Attribute : 문서의 구조를 구성하고 있는 요소
      • Text : 컨텐츠의 내용, 항상 단말 노드
      • Collection : 일종의 노드 집합
    • DOM 트리의 예

    <parent>
        <child  id="123">text here</child>
     </parent>
     

  • 인터페이스(API)
    • 객체의 속성과 메소드를 사용하기 위한 사양
    • DOM 인터페이스 예
      - 문서.childNodes[0].nodeName
      - 문서.firstChild.firstCild.firstCild.nodeName
      - 문서.firstChild.firstCild.firstCild.nodeValue

DOM level 1 주요 API

  • DOM Core Interface (Object Hierachy)
  • 주요 객체/속성/메소드
    • p.330-335 : 설명생략 - 진행하면서 지속적으로 참조
    • 주요 객체에 대한 속성과 메소드 (괄호안은 W3C 표준이 아니라  MS에서 제공)

    객체(Object)

    속성(Properties)

    메소드(methods) 

    Document 객체

    doctype,
    documentElement, implementation,
    (async, readyState)

    createAttribute, createCDATASection, createComment, createEntityReference, createElement, ..., createTextNode, getElementByTagName,
    (load, loadXML, save)

    Node 객체

    nodeName, nodeType, nodeValue, childNodes, firstChild, lastChild, nextSibling, ..., (text, xml)

    hasChildNodes, cloneNode,
    appendChild, insertBefore,
    removeChild, replaceChild

    Element 객체

    tagName

    getAttribute, getAttributeNode,
    removeAttribute, ...,
    setAttribute, setAttributeNode

    Attribute 객체

    name, value


    CharacterData 객체

    data, length

    appendData, deleteData, insertData, replaceData, substringData

DOM 프로그래밍 시작 - Document 객체

  • 문서 객체 새로 만들기 : DOMDocument 객체 생성
    • Msxml.DOMDocument 객체 새로 만들기
    • 또는 HTML에서 <xml> 태그 이용

    JavaScript (JScript)

    <Script language="Javascript">
       
    var xdoc
       
    xdoc = new ActiveXObject("Msxml.DOMDocument");
        ...
    xdoc.load("ex08.xml");;
    </script>
    VBScript 의 경우 <Script language="VbScript">
      Dim xdoc
      Set xdoc = CreateObject("Msxml.DOMDocument")
      ...
    xdoc.load("ex08.xml");
    </Script>

    HTML에서 <xml>  태그 이용

    - MSXML 파서 설치안한 경우

    <HTML> <HEAD>
        <Script language="Javascript">
            xdoc.load("ex08.xml");    </script>
    </HEAD>
    <BODY>
        <xml id="xdoc"></xml>
    </BODY> </HTML>
  • 기존의 XML 문서 읽기
    • DOMDocument 객체 읽기 - async 속성, load 메소드, xml 속성
    MSXML 파서 설치한 경우   MSXML 파서 설치안한 경우  
    <HTML>
    <HEAD>
    <Script language="Javascript">
    function xload0()
    {
       
    var xdoc = new
            ActiveXObject("Msxml.DOMDocument");
        xdoc.
    async = false;    xdoc.load("ex08.xml");
       
    alert(xdoc.xml);
    }
    </script>
    </HEAD>
    <BODY>
    <input type="button" value="XML 로드0"
        onClick="xload0()">
    </BODY>
    </HTML>
     
    <HTML>
    <HEAD>
    <Script language="Javascript">
    function xload1()
    {
        xdoc.async = false;
        xdoc.load("ex08.xml");

         alert(xdoc.xml);
    }
    </script>
    </HEAD>
    <BODY>
    <input type="button" value="XML 로드1"
        onClick="xload1()">
    <xml id="xdoc"></xml>
    </BODY>
    </HTML>
    VBScript 의 경우
    <Script language="VbScript">
      Dim xdoc
      Set xdoc = CreateObject("Msxml.DOMDocument")
      xdoc.
    async = False;
      xdoc.
    load("ex08.xml");  MsgBox  xdoc.xml
    </Script>
  • 신규 XML 문서의 작성
    • loadXML 메소드  
     xdoc.async = false;
     xdoc.
    loadXML( "<book><title>XML 입문</title><author>일지매</author></book>");
     alert(xdoc.xml);
     
     xdoc.async = false;
     xdoc.
    loadXML( "<book> <title> XML 입문 </title> <author> 일지매 </author> </book>");
     alert(xdoc.xml);
     
  • 공백의 처리 : preserveWhiteSpace 속성
     xdoc.async = false;
     xdoc.preserveWhiteSpace = true;
     xdoc.loadXML( "<book> <title> XML 입문 </title> <author> 일지매 </author> </book>");
     alert(xdoc.xml);
     
     xdoc.async = false;
     xdoc.preserveWhiteSpace = true;
     xdoc.load("ex07a.xml");
     alert(xdoc.xml);
     
  • XML 문서의 저장 : save 메소드
  • 에러 처리 : parseError 객체
    • parseError.errorCode, parseError.line, parseError.linepos, parseError.reason
     xdoc.async = false;
     xdoc.loadXML( "<book> <title> XML 입문 </title> <author> 일지매 </authors> </book>");
     alert(xdoc.xml);
     
     xdoc.async = false;
     xdoc.loadXML( "<book> <title> XML 입문 </title> <author> 일지매 </authors> </book>");
     if (xdoc.parseError)
        alert("에러 위치 : " + xdoc.parseError.line + "번째 라인 " + xdoc.parseError.linepos 
                  + "번째 문자\n\n에러 이유 : " + xdoc.parseError.reason);
     else
    alert(xdoc.xml);
     
  • 루트 노드 찾기 (루트 에리먼트)
    • documentElement 속성
     xdoc.async = false;
     xdoc.load("ex08.xml");
     var xroot = xdoc.
    documentElement;
     alert(xroot.nodeName);
     
     xdoc.async = false;
     xdoc.loadXML( "<book> <title> XML 입문 </title> <author> 일지매 </author> </book>");

     var xroot = xdoc.
    documentElement;
     alert(xroot.nodeName);

     

Node 객체의 정보구하기

  • 속성 : nodeName, nodeType, nodeValue, attributes, text 속성
  • nodeType
    • 1 (element), 2 (attribute), 3 (text) , 4 (CDATA), 5 (Entity Reference)...  : [p.348] 
  •  xdoc.load("ex08.xml");
     var xroot = xdoc.documentElement;
     alert('nodeName: '+xroot.nodeName+'\nnodeType: '+xroot.nodeType+
           '\nnodeValue: '+xroot.nodeValue+'\nattributes: '+xroot.attributes.length);
     alert(xroot.text);
     

실습 프로그램

  • 파일 LOAD 및 DOM 명령 실행 (교재 s20-03.htm 과 s20-05.htm 혼합)

    XML 파일 경로를 직접 입력 또는  '찾아보기'로 선택, 'LOAD'로 파일을 메모리에 로드
    경로 :  =>

    사용하고자 하는 DOM 구문을 아래에 입력하고 '확인' 버튼을 클릭  (예 : xdoc.text, xdoc.documentElement.firstChild.nodeName, ...) 구문 :   

     <SCRIPT language="Javascript">
            var xdoc, rootNode;
            function
    FileLoad()
            {
                    xdoc = new ActiveXObject("Msxml2.DOMDocument");
                    xdoc.async = false;
                    xdoc.load(
    path.value);
                    if (xdoc.parseError.errorCode != 0)
                        alert("파일을 메모리로 로드하는데 실패하였습니다 : " + xdoc.parseError.reason);
     
                    rootNode = xdoc.documentElement;
                    alert("[파일로드 성공] 루트 엘리먼트 : " + rootNode.nodeName);
            }
            function Execute()
            {
                    var selectionString;
                    try {
                            selectionString = eval(syntax.value);
                    } catch(e) {
                            selectionString = null;
                    }
                    alert(selectionString);
            }
    </SCRIPT>  
     ...
    <BODY>
     ... 경로 : <input  type="file"  size="40"  id="
    path">
         <input  type="button"  value="LOAD"  onclick="
    FileLoad()">
     ... 구문 : <input  size="50"  id="
    syntax"  value="xdoc.">&nbsp;
         <input  type="button" onclick="
    Execute()" value=확인>
     ...
    </BODY>


//------------------------------------------------------------------------------






1. DOM이란?

DOM(Document Object Model)이란 용어는 한동안은 웹 브라우저에 적용되었다. 현대의 브라우저는 객체 모델을 통하여 브라우저의 서비스에 프로그램저그로 액세스할 수 있도록 한다. 대표적인 예가 HTML페이지내의 스크립트 언어이다. 윈도우, 문서, 그리고 히스토리와 같은 객체는 BOM(browser object model)의 한 부분으로 취급되어왔다. 그러나 웹 개발이 갑자기 폭발적으로 증가하고 마이크로소프트와 넷스케이프 사이의 경쟁으로 인하여 이 모델은 서로 다르게 구현되었고 동일한 코드를 적용하기가 어려워졌다. 웹에서 문서 구조를 액세스하고 조작하는 좀 더 표준적인 방법을 만들기 위해서 W3C는 현재의 W3C DOM이라는 스펙을 내놓았다. 이 스펙은 HTML문서에 대한 객체 모델과 XML문서에 대한 좀 더 일반화되 모델을 제공한다.

W3C DOM은 언어 중립적(language-neutral)이고 플랫폼 중립적(platform-neutral)인 정의이다. 즉, DOM을 구성하는 다른 객체에 대해 인터페이스는 정의하지만, 구현에 대해서는 어떤 스펙도 제공하지 않는다. DOM안에 있는 객체는 개발자가 문서로부터 데이터를 읽고, 탐색하고, 변경하고, 추가하며, 삭제할 수 있도록 한다. 또한 문서항해를 위한 표준적인 기능 정의를 제공하고, HTML문서와 XML문서의 내용과 구조를 조작할 수 있는 기능을 제공한다.

DOM은 어떤 플랫폼에서 어떤 프로그래밍 언어로도 구현할 수 있다. 예를 들어 DOM인터페이스를 데이터 액세스 함수들에 대한 랩퍼(wrapper)로 구현함으로써 데이터 저장소를 DOM을 사용하여 액세스할 수 있다.


2. DOM을 사용하는 이유

XML문서를 생성하고 액세스하기 위해서 DOM을 사용하면 다음과 같은 몇 가지 장점을 얻을 수 있다.

· DOM은 문법이 적절하고 well-formed 임을 보여준다.
· DOM은 문법으로부터 내용을 추출한다.
· DOM은 내부 문서 조작을 단순화한다.
· DOM은 전형적인 계층적 또는 관계형 데이터베이스 구조와 거의 유사하다.

이러한 내용에 대해 좀더 자세히 살펴보자.

(1) DOM은 문법이 적절하고 Well-formed임을 보장한다

DOM파서는 텍스트 파일을 노드 트리의 추상적 표현으로 변환하기 때문에, 당혀지지 않은 테그나 부적절하게 중첩된 태그와 같은 문제는 완벽하게 피할 수 있다. 게다가 DOM은 문서에서 부적절한 부모-자식 관계를 허용하지 않는다. 예를 들어 Attr객체는 다른 Attr객체의 부모가 될 수 없도록 만들 수 있다.

(2) DOM은 문법으로부터 내용을 추출한다

DOM에 의해 생성된 노드 트리는 XML 파일에서 발견할 수 있는 내용의 논리적이고 일관된 표현이다. 이것은 어떤 정보가 존재하는지, 그리고 XML 문법에 꼭 국한되지 않고도 어떻게 관계를 갖는지를 보여준다. 예를 들어, 노드에 의해 노출된 정보는 관계형 데이터베이스를 변경하거나 HTML페이지를 생성하기 위해 사용할 수 있다. 그리고 개발자는 XML언어의 세부 사항을 알 필요가 없다.

(3) DOM은 내부 문서 조작을 단순화한다

DOM을 사용하여 XML 파일을 수정하는 개발자는 손으로 같은 일을 하는 사람보다 좀더 쉽게 작업할 수 있다. 앞 예제에서 언급했던 것처럼, 문서의 중간에 요소를 추가하는 것 정도는 DOM을 사용하면 간단히 처리할 수 있다. 게다가 전역 처리는 몇 개의 명령을 혼합하여 수행할 수 있다. 만일 DOM을 사용하지 않는다면 파일을 직접 스캔하고 해당 태그들을 직접 제거해야 한다.

(4) DOM은 전형적인 계층적 또는 관계형 데이터베이스 구조와 거의 유사하다

DOM이 데이터 요소 사이의 관계를 표현하는 방법은 현대의 객체 지향형 데이터베이스와 관계형 데이터베이스에서 정보를 표현하는 방법과 매우 유사하다. 이는 데이터베이스와 DOM을 사용하는 XML 파일 사이의 정보 이동을 매우 쉽게 만든다.많은 데이터베이스는 눈송이 구조를 사용하여 계층적 정보를 표현한다. 이것은 차바퀴의 살과 같이 데이터베이스 안에 있는 정보가 중앙에 있는 '꼭대기 단계'테이블로부터 방사된다.

3. DOM 핵심 인터페이스에 대한 개관

이 절에서는 객체들과 문서 객체들을 가져오고 사용하기 위한 인터페이스에 대해 최소한의 정의를 내린다. DOM을 따르는 제품들에서는 이 절에서 명시된 기능(핵심 기능)을 이용하면, 소프트웨어 개발자들이나 웹 스크립트 작성자들이 분석된 HTML이나 XML의 내용을 가져와서 사용할 수 있다. 또한 DOM 핵심 API는 단지 DOM API 호출을 사용함으로서 문서 객체를 구축한다; 문서의 기본골격을 생성하고, 지속적으로 저장, 관리하는 것은 DOM API를 구현한 제품에서 수행해야 할 것이다.

(1) DOM 구조 모델

DOM은 문서를 노드 객체들의 계층구조로서 나타낸다. 각각의 노드 객체들은 특별한 인터페이스들을 제공한다. 문서의 구조에 있어서, 어떤 타입의 노드는 여러 가지 종류의 자식노드들을 가질 수 있고, 다른 노드는 하위에 아무것도 가지고 있지 않은 단말 노드들이 될 수 있다. 자식 노드로서 가질 수 있는 노드의 타입은 다음과 같다.

문서
문서조각
문서타입
엔터티참조
엘리먼트
속성
처리명령
주석
텍스트
CDATA섹션
엔터티
Notation(표기)

엘리먼트(maximum of one), 처리명령, 주석, 문서타입
엘리먼트, 처리명령, 주석, 텍스트, CDATA섹션, 엔터티참조
자식없음
엘리먼트, 처리명령, 주석, 텍스트, CDATA섹션, 엔터티참조
엘리먼트, 텍스트, 처리명령, CDATA섹션, 엔터티참조
텍스트, 엔터티참조
자식없음
자식없음
자식없음
자식없음
엘리먼트, 처리명령, 주석, 텍스트, CDATA섹션, 엔터티참조
자식없음

DOM은 NodeList 인터페이스를 명시한다. 이것은 노드의 자식, 또는 Element 인터페이스의 getElementsByTagName 메소드에 의해서 리턴되는 엘리먼트와 같이, 노드들의 정렬된 리스트들을 다루기 위해서 사용된다. 그리고 또한 이름 속성에 의해서 참조되는 노드들의 정렬되지 않은 집합을 다루기 위해서 NameNodeMap 인터페이스를 명시한다. 이것은 DOM에서 Element. NodeList나 NamedNodeMap의 속성들이 "살아있는" 것, 즉, 기본적인 문서 구조의 변화들이 모든 관련된 NodeList나 NameNodeMap에 반영된다는 것이다. 예를 들어 만약 DOM 사용자가 한 엘리먼트의 자식을 포함하고 있는 NodeList 객체를 얻고, 이어서 그 엘리먼트에 자식노드들을 추가한다면 (또는 자식노드를 삭제하거나, 수정한다면), 이러한 변화가 사용자 측면에서 다른 작용없이 자동적으로 NodeList에 반영되어야 한다. 더욱이 트리안의 노드에 대한 변화가 NodeList나 NameNodeMap안의 노드에 대한 모든 참조에서도 반영되어야 한다.

마지막으로, 텍스트, 주석, CDATA섹션의 인터페이스들은 CharacterData 인터페이스로부터 모두 상속받는다.

(2) 메모리 관리

이 스펙에서 정의된 대부분의 API들은 클래스라기 보다는 인터페이스이다. 이것은 실제로 인터페이스에 정확히 일치하는 클래스를 구현하는 것이 아니라 단지, 정의된 이름과 지정된 동작을 가진 메소드를 나타낼 수 있도록 실제로 구현하는 것이다. DOM API는 자신의 데이터 구조를 가지고 있던 애플리케이션들 위에, 또는 전혀 다른 클래스 구조를 가진 새로운 애플리케이션들 위에 얇은 겉포장으로 구현될 수 있다. 이것은 또한 일반적인 작성자(자바나 C++에을 사용하는)가 DOM 객체들을 생성하기 위해 사용될 수 없다는 것을 의미한다. 왜냐하면 이미 구성되어 있는 기본적인 객체들이 DOM 인터페이스와 전혀 관계가 없기 때문이다. 객체지향 디자인에서 이것에 대한 상투적인 해결책은 여러 인터페이스들을 구현한 객체의 인스턴스를 생성하는 factory 메소드를 정의하는 것이다. 어떤 인터페이스 "X"를 구현하는 객체들은 Document 인터페이스에서 "CreateX()"메소드에 의해서 생성된다; 이것은 모든 DOM 객체들이 지정된 문서의 내용에 존재하기 때문이다.

DOM 레벨 2 API는 DOMImplementation 또는 Document 객체를 생성하기 위한 표준 방식을 정의하지는 않는다; 실제 DOM을 구현할 때, 이러한 DOM 인터페이스를 동작시키는 어떤 방식을 제공해야만 한다. 그리고 나서 다른 모든 객체들은 Document의 Crate 메소드(또는 다른 편리한 메소드)로부터 만들어질 수 있다.

핵심 DOM API들은 일반적인 사용자의 스크립트 언어들이나, 대부분 전문 프로그래머들에 의해 사용되는 간단하지 않은 언어들까지 포함해서, 다양한 언어들과 호환되도록 디자인되어 있다. 그래서 DOM API들은 다양한 메모리 관리 방침을 사용해 작동할 필요가 있다. 메모리 관리가 사용자에게 전혀 드러나지 않는 언어의 플랫폼들에서부터, 사용하지 않는 메모리를 자동으로 다시 요구하는 자동 쓰레기 수집(automatic gabage collection)을 제공하지만 제작자에게 명시적으로 보여주는 언어(자바와 같은 언어)들 뿐만 아니라, 일반적으로 프로그래머가 명시적으로 객체에 메모리를 할당하고, 어디에서 사용되는지 추적하고 재사용을 위해 직접 해제하는 것을 요구하는 언어(특히 C/C++)들까지 포함하기 위해서이다. 이러한 플랫폼들 사이에 일관된 API를 보장하기 위해서 메모리 관리문제를 전혀 다루지 않고 대신 구현시에 수행할 수 있도록 하고 있다. DOM 워킹그룹(ECMA Script 와 자바를 위한)에 의해서 고안된 명시적인 언어 규칙중 어느 것도 메모리 관리를 위한 메소드를 요구하지 않는다. 그러나 다른 언어(특히 C나 C++)를 위한 DOM 규칙은 아마도 이러한 메모리 관리 지원을 요구할 것이다. 그러나 이것은 DOM 워킹 그룹이 아니라, 특정 언어로 DOM API를 적용하려는 사람들이 확장시켜야 할 것이다.

(3) 이름 관행 (Naming Convention)

속성이나 메소드의 이름들이 짧고, 정보량이 많고, 내부적으로 일관되고, 유사한 API의 사용자들에게 친숙한 것은 좋은 반면에, 이러한 이름들이 DOM 구현시 지원되는 옛날의 API들에서 사용되는 이름들과 충돌하지 않아야만 한다. 더구나 OMG IDL과 ECMAScript 둘다 이름의 충돌을 피하기 위한 능력에서 커다란 한계를 가지고 있다. 그래서 DOM 이름들은 모든 환경에서 유일하기 위해서 길고 아주 설명적인 경향이 있다.

또한, 워킹 그룹은 다른 API에서의 이름의 구별과 다를지라도, 여러 용어의 사용에 있어서 내부적인 일관성을 유지하려고 시도하고 있다. 예를 들어, 구조 모델을 바꾸는 메소드는 "remove"란 메소드 이름을 사용하고, 구조 모델 내부의 무언가를 제거하는 메소드를 "delete"란 메소드 이름으로 사용한다. "delete"되는 것은 리턴되지 않고, "remove"된 것은 성공하면 리턴되어질 것이다.

(4) API의 상속과 Flattened View

DOM 핵심 API들은 XML/HTML 문서에 대한 두 개의 약간 다른 부류의 인터페이스들을 나타낸다; 하나는 상속이란 계층을 가지는 "객체 지향"적인 접근을 나타내는 것이고, 다른 하나는 모든 조작들이 Node 인터페이스를 통해서 수행되도록 하는 "단순화된" 관점을 나타낸다. 이 Node 인터페이스는 COM 환경에서 호출하는 질의 인터페이스나 외형적인 형태(자바나 C와 같은 언어들에서처럼)를 요구하지 않는다. 이러한 두가지의 동작들은 자바와 COM에서 상당히 많은 비용이 들어가고 그래서 DOM은 성능이 중요한 요소로 작용하는 환경에서 사용되어 질 것이다. 그러므로 단지 Node 인터페이스를 사용함으로서 중요한 기능을 사용할 수 있게 하고 있다. 또, 많은 사용자들이 DOM에서 "모든 것을 노드"로 접근하는 것보다 계층적인 상속을 더 쉽다고 느끼기 때문에, 객체 지향 API를 선호하는 사람들을 위한 보다 높은 레벨의 인터페이스도 지원할 것이다.

실제로, 이것은 API에서 상당한 중복을 초래할 수 있다. 워킹 그룹은 "상속"의 접근을 API의 주요 관점으로 고려하고 있고 그리고 Node에서 전체 기능은 사용자들이 필요로 하는 "여분의" 기능으로 검토하고 있다. 그러나 그것은 객체지향 분석을 강요하는 다른 인터페이스들에서 메소드를 위한 요구를 무시하지는 않는다. (물론, 객체지향 분석이 노드 인터페이스와 같은 속성이나 메소드를 만들어 낼 때, 중복되었다는 것을 명시하지는 않는다.) 그래서, Node 인터페이스에서 일반적인 NodeName 속성이 있을지라도, 여전히 엘리먼트 인터페이스에서의 tagName 속성이 존재한다; 이러한 두가지 속성들은 DOM API가 만족해야하는 다른 구성요소에서 주어진 같은 값을 가지고 있지만, 워킹 그룹은 두가지 모두 지원할 가치가 있다고 여기고 있다

(5) DOMString 타입

상호교환을 위해서, DOM은 다음과 같이 DOMString 타입을 명시하고 있다.

Type Definition DOMString

이때의 DOMString은 연속적인 16비트 길이이다.

IDL Definition

typedef sequence<unsigned short> DOMString;

애플리케이션들은 UTF-16을 사용해서 DOMString을 인코딩 해야한다. UTF-16 인코딩은 광범위한 연구 실행 때문에 선택되어졌다. HTML과 XML을 위한 문서의 문자셋(그리고, 숫자참조를 위한 표기)은 UCS[ISO-10646]에 기반을 두고 있음을 유의해야 한다. 어떤 경우에 소스문서에 있어서 하나의 숫자 참조는 DOMString에서 2개의 16비트 유닛과 일치할 수 있다.

메모: DOM이 문자열 타입의 이름을 DOMString이라고 정의한다 할지라도, 바인딩시에 다른 이름들을 사용할 수 있다. 예를 들어 자바에서 DOMString은 인코딩으로서 UTF-16을 사용하기 때문에 String 타입으로 사용된다.

메모: 1998년 8월, OMG IDL 스펙은 wstring 타입을 포함하고 있다. 그러나 문자의 길이를 결정하는 인코딩 협상에 의존하고 있기 때문에 DOM API의 상호교환을 위한 기준을 제공하지 못하고 있다.

(6) DOM에서 문자열 비교

DOM은 문자열 일치를 내포하고 있는 많은 인터페이스들을 가지고 있다. HTML 프로세서들은 일반적으로 엘리먼트로서 표준 이름을 대문자(가끔, 소문자)로 가정한다. 반면에 XML은 명시적으로 대소문자를 구분한다. DOM의 목적에 있어서, 문자열 일치는 DOMString의 16비트 단위의 이진비교로 수행된다. 그래서 DOM 구조가 만들어지기 전에, 어떤 표준화가 해당 프로세서 안에서 정해질 것이라고 DOM은 가정한다.

메모: 이것은 무슨 표준화가 발생하는냐에 대한 논쟁을 야기한다. W3C 118N 워킹 그룹은 어떤 표준화가 DOM을 구현하는 애플리케이션을 위해 필요한지를 정의하고 있는 중이다.

(7) XML Namespaces

DOM 레벨 2는 namespace와 연관된 엘리먼트나 속성들을 생성하고 조작하기 위한 DOM 레벨 1의 몇가지 인터페이스들을 확대함으로서 XML Namespace들을 지원한다.

DOM에 관한한, XML namespace를 선언하기 위해 사용된 특별한 속성들은 다른 속성들과 같이 다루어질 수 있다. 그러나 노드들은 생성되어진대로 영구적으로 namespace URI들과 연결되어야 한다. 그 결과 DOM의 사용에 있어서, 문서내에서 노드를 이동하는 것은 어떤 경우라도 namespace prefix나 namespace URI의 변화를 가져오지는 않는다. 유사하게, namespace prefix와 namespace URI를 가진 노드의 생성이나, 노드의 namespace prefx를 변경하는 것은, 적절한 XML namespace를 선언하기 위한 특별한 속성들의 추가, 제거, 수정을 초래하지는 않는다. Namespace의 유효성을 강요하지는 않는다.; DOM의 구현에 책임이 있다. 특히 prefix들과 namespace URI들이 강요되지 않기 때문에, 일반적으로 결과 문서는 일관적이지 않다. 예를들어, 애플리케이션은 문서가 연속적일 때 사용중인 모든 namespace를 선언할수 있다.

namespace가 없는 문서에서, 엔터티참조 노드의 자식 리스트는 항상 관계된 엔터티와 같다. 이것은 엔터티가 연결되지 않은 namespace prefix를 포함한 문서에서는 진실이 아니다. 그러한 경우에 관계된 엔터티참조의 자손들은 엔터티 참조에 의존하고 있는 다른 namespace URI들과 연결되어 있다. 더욱이, DOM에서 노드들은 항상 같은 namespace URI들과 연결되기 때문에 엔터티 참조 노드를 이동하는 것은 serialize하지 않은 문서를 발생하게 한다.
이것은 또한 다음측면에서 사실이다. DOM 레벨 1 메소드 Document 인터페이스의 createEntityReference가 엔터티에 일치하는 엔터티 참조를 생성하기 위해 사용되어 질 때 리턴된 엔터티참조의 자손들이 연결되지 않기 때문이다. DOM 레벨 2는 namespace prefix를 해결하기 위한 어떠한 구조도 지원하지 않는다. 이런 모든 이유 때문에, 엔터티와 엔터티 참조의 사용은 피하거나 극도로 조심스럽게 사용되어 진다. DOM의 다음 레벨에서는 이것을 다루기 위한 몇 개의 부가적인 지원을 포함할 것이다.

Document 인터페이스의 createElementNS와 createAttributeNS와 같은 새로운 메소드들은 namespace에 정통한 애플리케이션에서 사용되어지도록 정의되어 있다. namespace를 사용하지 않는 단순한 애플리케이션은 createElement나 createAttribute같은 DOM 레벨 1 메소드들을 사용할수 있다. 이러한 방식으로 생성된 엘리먼트들이나 속성들은 namespace prefix, namespace URI, 그리고 local name을 가지고 있지는 않다.

메모 : namespace를 다루지 않을 때 DOM 레벨 1을 사용하는 것은 안전한 반면에, 동시에 새로운 것들을 사용하는 것은 피해야만 한다. namespace와 관계가 없는 DOM 레벨 1 메소드들은, nodename에 의해서만 속성 노드들을 식별해야 한다. 반대로, namespace와 관련된 DOM 레벨 2 메소드들은 namespaceURI와 localName에 의해서 속성노드들을 식별할 수 있다. 이러한 기본적인 차이 때문에, 두 부류의 메소드들을 혼합하는 것은 예측하지 못한 결과들을 가져오게 된다. 특히, setAttributeNS를 사용하는 것은 하나의 엘리먼트에 같은 nodeName을 가지고 있지만, 다른 namespaceURI를 가지고 있는 두 개 이상의 속성을 설정할 수 있다. 그러한 nodeName에서 getAttribute를 호출하는 것은 여러 속성들중의 어느 하나를 리턴할 수 있다. 그결과는 구현에 의존적이게 된다. 유사하게 setAttributeNode를 사용하는 것은 같은 prefix와 namespaceURI를 가지고 있지만 다른 nodeName을 가지고 있는 두 개 이상의 속성을 설정할 수 있다. 이러한 경우에 getAttributeNodeNS는 플랫폼에 의존해서, 어느 하나를 리턴할 것이다. 그러한 경우에 유일한 보장은 setAttribute와 setAttributeNS가 각각 getAttirbute와 getAttributeNS가 리턴한 노드에 영향을 주는 것이다.



//------------------------------------------------------------------------------






1. DOM의 여러가지 타입

DOM은 XML에서 뿐만 아니라 HTML안의 객체 모델에 대한 필요성을 말하고 있다. Well formed HTML문서 역시 XML문서이기 때문이다. XMLDOM은 CoreDOM으로 언급된다.

(1) DOM Level 1

core, HTML & XML 문서 모델에 관한 내용을 담고 있다.
navigation & manipulation

[특징]

1) Core DOM 기반으로 HTML 문서 핸들링을 위한 인터페이스

2) HTML에 맞는 인터페이스만 추가로 정의

3) HTML4.0에 정의 된 모든 태그에 대해 각각의 타입 등록

4) HTML 태그 각 고유의 추가적인 속성 및 기능 지님

(2) DOM Level 2

style sheet를 적용한 객체 모델 지원한다.
문서에 대한 style 정보를 manipulation하는 기능을 정의한다.

[특징]

1) 문서의 문맥과 구조 그리고 스타일을 동적으로 접근하고 갱신하기 위한 플랫폼, 중간 언어 인터페이스

2) XML, HTML, 추상적 뷰, 일반적 스타일 시트, CSS, 이벤트, 문서 구조와 객체 범위의 변화를 결정하기 위한 구체적인 인터페이스

3) DOM Level 1 Core을 기반으로 작성

4) DOM Level 1 Core Vs. DOM Level 2 Core
     DOM Level 2 specifications 은 CORBA 2.2 대신 CORBA 2.3.1 을 사용
     DOM Level 1 Core interfaces와 exceptions 변화
     Type의 변화

5) DOM Level 2 Views
     DOM Level 2 Core기반에서 작성
     문서를 표현하는 내용을 업데이트
     동적으로 접근하기 위한 스크립트나 프로그램을 위한 인터페이스를 정의

6) DOM Level 2 Events
     DOM Level 2 Core 와 DOM Level 2 Views 에서 프로그램
     일반적인 이벤트 시스템에 스크립트나 프로그램을 위한 인터페이스 정의

7) DOM Level 2 Style
     DOM Level 2 Core와 DOM Level 2 Views 기반 위에서 작성
     문서의 스타일이나 내용을 업데이트
     스크립트나 프로그램을 작성하는 인터페이스나 DOM Level 2 Style Sheets , CSS를 정의

(3) DOM Level 3

DOM Level 2 Core 에 기반을 두고 있다.
Namespace나 문서의 스타일, 내용, 구조에 동적 접근 및 갱신이 가능한 확장 인터페이스를 제공해 준다.

[특징]

1) DOM Level 2 Event Specification에 명시된 기능을 확장

2) DOM Level 2에 이미 정의된 modules을 새로운 인터페이스로 추가

3) DOM Level 2에 이미 정의된 interface들을 기본으로 설계

4) Core Requirements

     White space 처리
     XML 선언과 CDATASection 선언의 명확성 구분
     특정 클래스를 사용하기 위해 Java에서 DOM 로딩
     노드 식별
     Namespace의 검색과 수정
     예외사항 처리
     노드 정렬 처리
     다른 문서로의 노드 이동(Moving)

5) Events Requirements

     Level2 의 Events Spec에서 처리되지 않고 언급되지 않은 Event들을 처리
     EventListener grouping
     Key event set
          키보드 입력을 다루는 Key event들의 집합
     Input event set
          키보드 입력에 기반한 IME(Input Method Editor)를 다루는 Input event들의 집합
     Device independent event set

DOM Level 0의 스펙은 존재하지 않지만 타이틀은 마이크로소프트 인터넷익스플로러 3과 넷스케이프3에서 나타난 HTML DOM의 결합을 언급하고 있다.

2. 트리모델

XML은 계층언어이다. XML문서에 포함되어 있는 태그들은 부모자식관계를 가지고 있다. 때문에 자연스럽게 트리로 표현할 수 있다. DOM스펙에서는 XML내부문서의 구조가 트리여야만 된다고 언급하지는 않는다. 차라리 인터페이스의 집합이 직접적으로 트리모양의 개념적인 모델로 이끌고 있다.

즉 다시 말하자면 DOM인터 페이스가 XML문서를 트리로 표현한다는 것을 파서의 사용자에게 알려준다.

XML문서안의 앨리먼트 또는 애트리뷰트와 같은 각 구조는 트리안에서 노드로 표현되고, 이 트리 표현법은 객체지향원칙으로 디자인되어 있다. XML구조를 표현하는 노드들은 그들 각 고유의 프로퍼티와 메소드 집합을 가지고 있고 기본클래스로부터 기능을 공유하게 된다. 모든 노드에 있는 몇몇 기능은 트리를 검색하는데 필요한 메카니즘과 노드의 내용을 조작할 능력을 포함하고 있다.

(1) 기본 인터페이스

1) DOM Exception

DOM operations의 예외적인 상황에서 예외 처리

2) DOM Implementation

Operation를 수행하기 위한 많은 method 제공

3) DocumentFragment

"lightweight" or "minimal" Document object

4) Document

HTML 또는 XML 문서 표현
문서의 root는 tree를 개념적으로 표현

5) Node

DOM의 주된 datatype
document tree에서 단일 노드 표현

6) NodeList

Node들의 집합에서 node의 추출

7) NamedNodeMap

Name으로 접근할 수 있는 node들을 나타내는데 사용
NodeList로 부터 상속을 받지 못함

8) CharacterData

character data 의 method나 attributes의 집합을 가진 확장된 Node

9) Attr (Attribute)

Element object의 속성을 표현

10) Text

Element 나 Attr의 문맥적 내용을 표현

11) Comment

주석을 표현

(2) 확장 인터페이스

1) DocumentType

엔티티 정보, Notation 정보, DTD 문서형을 취급

2) Entity

DocumentType의 속성값으로 DOM 트리 구성에서 제외
EntityReference에 의해 DOM 트리에 삽입

3) EntityReference(엔티티 참조)

4) Notation(표기법 선언)

5) ProcessingInstruction(처리명령)

6) CDATASection(CDATA 섹션 처리)

(3) DOM 인터페이스의 개념적 구조


//------------------------------------------------------------------------------






1. 여러가지 다른 노드 타입

각 노드 타입은 Node라고 부르는 기본클래스로부터 파생되었다. 개발자는 고유의 노드를 생성하지는 않지만 다음에 나타나는 노드들 중 하나를 생성하여 XML문서의 한부분에 대한 적당한 행위를 수행할 수 있다. 이러한 노드들은 각각 nodeType 프로퍼티를 통하여 그들 자신을 식별할 수 있는데, 이는 숫자가 모든 노드에 배정되고 nodeType은 특별한 노드에 연결된 숫자를 반환하여 준다.

또한 노드는 이름과 값을 가지고 있다.

nodeType
nodeType에 따른 숫자
Element
1
Attribute
2
Text
3
CDATASection
4
EntityReferance
5
Entity
6
ProcessingInstruction
7
Comment
8
Document
9
DocumentType
10
DocumentFragment
11
Notation
12


(1) Document

Document 노드는 마스터 노드이다. 많은 노드들중에 오직 하나만이 XML문서를 위하여 존재할 수 있다. 이 노드는 맨위에 있는 부모노드이고 XML문서 전체를 표현한다. 즉, Document는 XML문서의 특정부분을 나타내는 것이 아니라는 것이다. 그리고 이 노드는 다른 노드를 생성하는 기능을 가지고 있다.

(2) NodeList

NodeList 노드는 자식 노드들을 유지하기 위하여 사용되는 노드이다. 현재 얼마나 많은 자식들이 있는지, 반복구조 기능을 이용할 수 있는 특징을 가지고 있는지를 부모노드에게 알려준다. 하지만 모든 노드가 NodeList 콜렉션을 가질 수 없다. 왜냐하면 NodeList는 개념적으로 주어진 자식노드들에게 접근하기 위한 도구일 뿐이기 때문이다. 즉, 자식노드를 그룹화 시키는데 사용할 뿐이다.

(3) NamedNodeMap

NodeList와 비슷하지만 그들의 이름을 사용하여 자식노드에 접근하는 부가 기능을 가지고 있다. 이 기능은 애트리뷰트에 접근하고자 할때 필요하다. 그 결과로 NamedNodeMap 노드는 애트리뷰트 노드를 유지하는데 사용된다는 얘기다.

(4) Element

Element 노드 타입은 XML문서에 있는 엘리먼트를 포함한다. 그리고 엘리먼트안에 선언된 애트리뷰트에 접근해서 관리하는 특별한 도구를 가지고 있다. Element노드는 Document노드의 자식인 맨위에 존재하는 엘리먼트를 제외하고는 모두 다른 엘리먼트의 자식들이다. 이때 맨위에 존재하는 Element를 documentElement라고 말하며, 바로 Root Element이다.

<root>
    <some/>
</root>


위의 예제에서 <root>는 Document노드의 자식이고, <some>은 root Element 노드의 자식이다.

(5) Text

Text 노드는 태그안에 포함된 엘리먼텍스트를 나타낸다. 다음의 XML문서는 name Element 노드의 자식인 Text 노드를 만든다. 이 Text 노드는 'Mydosu'라는 값을 포함하고 있다.

<root>
    <name>Mydosu</name>
</root>

(6) Attr(Attribute)

Attr 노드 타입은 엘리먼트 범위안에 선언된 애트리뷰트를 나타낸다. 다음 XML 예제를 자세히 보도록 하자.

<root myatt="value"/>

이 예제의 트리보델은 다음과 같다. 애트리뷰트에 관여하는 노드와 마지막의 text 노드도 눈여겨 보도록 하자.

(7) CDATASection

CDATASection 노드는 Text 노드와 비슷하지만 마크업을 포함 할 수 있다.

<root><![CDATA[<b>Kim</b>]]></root>

(8) DocumentType

DocumentType노드는 DTD의 작은 부분 집합이다. DTD의 전부를 보여 주지 못한다는 것이다. 단지 <!ENTITY>와 <!NOTATION>만을 나타낸다.

<!DOCTYPE root [
<!ELEMENT root (#PCDATA)>
]>
<root>TEXT</root>

(9) Entity

Entity 노드는 DTD에서 사용된 <!ENTITY> 태크표현방식을 제공해 준다. 이때 Entity노드의 부모노드는 DocumentType 노드이다. system id, public id, notation name과 같은 엔티티의 여러가지 프로퍼티가 Attr 노드로 모델화 되고 Entity 노드의 자식으로 자리잡는다.

(10) Notation

Notation 노드는 DTD에서 사용된 <!NOTATION> 태크표현방식을 제공해 준다. 이때 Notation 노드의 부모노드는 DocumentType 노드이다. system id, public id, notation name과 같은 엔티티의 여러가지 프로퍼티가 Attr 노드로 모델화 되고 Notation 노드의 자식으로 자리잡는다.

<!DOCTYPE root [
<!ELEMENT root (#PCDATA)>
<!ENTITY sample SYSTEM "http://ss.hh.com/sample.xml">
<!NOTATION gif SYSTEM "http://ss.hh.com/gif/gifviewer.exe">
]>
<root>TEXT</root>



(11) ProcessingInstruction

ProcessingInstruction 노드는 PI를 표현한다. Document 노드의 자식이다.

(12) Comment

Comment 노드는 <!-- -->를 표현한다. Comment 노드는 XML구조에 관한 주석을 XML문서 트리에 삽입한다.

(13) DocumentFragment

DocumentFragment 노드는 Document 노드의 일부분이다. 이 노드는 이동할 때 위치소유자가 사용된다. 이 노드는 Document 노드의 충분한 능력을 갖고 있지 않다. 왜냐하면 트리에 재입력되는 노드를 위한 임시기억장소이기 때문이다.

다음의 예제 XML을 이용하여 DOM tree 구조를 각자 그려 보도록 하라.

<?xml version="1.0" encoding="euc-kr">

<GOODSLIST>
<!-- Result from a query -->
   <good no="1012345">
      <name>빠삐코</name>
      <price>500원</price>
   </good>
   <good no="2022346">
      <name>맛동산</name>
      <price>600원</price>
   </good>
</GOODSLIST>



//------------------------------------------------------------------------------






1. 기본 사용법

이 강의에서 기본적으로 사용하는 방법에 대해서 말하겠다. 일단 간단한 예제를 사용하기 위한 브라우저와 자바스크립트를 이용할 것이니까 HTML을 바탕으로 하는 것이 좋겠다. HTML을 바탕으로 한다면 XML문서를 데이터섬으로 불러서 활용하면 되겠다.

기본형태를 한번보면 이해할 것이다.

<HTML>
<HEAD>
<TITLE> New Document </TITLE>
</HEAD>

<BODY>

<xml id="xml">
<root>
<element1/>
<element2/>
<element3/>
</root>
</xml>

<script language="javascript">

var rootNode=xml.documentElement;
var alsoRootNode=xml.childNodes.item(0);

var element1=xml.documentElement.childNodes.item(0);
var element2=rootNode.childNodes.item(1);
var element3=xml.childNodes.item(0).childNodes.item(2);

confirm(rootNode.nodeName);
confirm(xml.xml);
</script>

</BODY>
</HTML>


뭐...대충 이런식이다. 예전에 배운것처럼 일단 예제용 XML문서를 하나 만들어 두고 그 파일을 링크 시킨 다음 사용해도 된다.

일단 이번 강의의 목적은 표준 DOM을 익히는 것이다. Application 마다 고유한 파싱과 메소드들을 제공해 주는 것도 있지만 일단 표준을 알고 지나가는 것이 좋을 것이다.

2. 모든 것이 Node

일단 DOM Level 1에서 보았던 그림을 한번 더 보자

위의 그림은 클래스의 상속성을 나타내기도 한다. 그림에서 처럼 부모를 가지고 있는 모든 클래스는 부모가 가지고 있는 모든 프로퍼티와 메소드를 얻게 된다. 즉, Node에서 시작된다는 것이다. 하지만 Node는 다른 클래스를 파생시킬때만 사용되고 직접적으로 나타나지는 않는다.

그리고 NodeList와 NamedNodeMap노드는 예외다. 이것은 기본 클래스를 가지지 않는다.

3. Node

(1) 부모노드

Node의 부모노드는 없다.

(2) Node Propeties

1) nodeName

타 입
DOMstring
설 명
노드의 이름을 나타낸다. 이 프로퍼티가 사용되는 노드의 타입에 의거하여 결과 값이 변한다. 아래 표는 중요하게 사용되는 nodeName의 노드타입은 Element와 Attribute인것을 보여준다.

노드타입
nodeName 프로퍼티
Document
Element
Attribute
Text
CDATASection
Comment
Entity
Notation
EntityResference
PricessingInstruction
DocumentType
DocumentFragment

#document
element
attribute
#text
#cdata-section
#comment
entity name
notation name
name of entity resferenced
target(the first word following the <?)
document type name
#document-fragment


<HTML>

<BODY>

<script language=javascript for=window event="onload">
confirm(xml.documentElement.nodeName);
confirm(xml.documentElement.attributes.item(0).nodeName);
</script>
<xml id = "xml">
<엘레먼트이름 애트리뷰트이름 = "hello" />
</xml>
</BODY>
</HTML>


2) nodeValue

타 입
DOMstring
설 명
노드안에 포함된 데이터를 나타낸다. 이 프로퍼티가 사용되는 노드의 타입에 의존하여 결과 값이 변한다. 아래 표는 nodeValue의 행위를 보여준다.

노드타입
nodeName 프로퍼티
Document
Element
Attribute
Text
CDATASection
Comment
Entity
Notation
EntityResference
PricessingInstruction
DocumentType
DocumentFragment

null
null
attribute value
text
text
comment text
null
null
null
text(target안에 있는 노든 내용)
null
null


3) nodeType

타 입
unsigned short
설 명
노드타입을 나타내는 정수를 알려준다. 아래표는 노드타입에 따른 정수값이다.

nodeType
nodeType에 따른 숫자
Element
1
Attribute
2
Text
3
CDATASection
4
EntityReferance
5
Entity
6
ProcessingInstruction
7
Comment
8
Document
9
DocumentType
10
DocumentFragment
11
Notation
12

<HTML>
<BODY>

<script language=javascript for=window event="onload">
confirm(xml.documentElement.nodeName);
confirm(xml.documentElement.nodeType);
confirm(xml.documentElement.attributes.item(0).nodeValue);
confirm(xml.documentElement.attributes.item(0).nodeType);
confirm(xml.documentElement.attributes.item(1).nodeValue);
confirm(xml.documentElement.attributes.item(1).nodeType);
confirm(xml.documentElement.childNodes.item(0).nodeValue);
confirm(xml.documentElement.childNodes.item(0).nodeType);
</script>

<xml id = "xml">
<someElement someAttribute = "애트리뷰트값" nextAttribute="두번째애트리뷰트값">
엘리멘트 내용을 기술하세여!
</someElement>
</xml>

</BODY>
</HTML>

4) childNodes

타 입
nodeLiat
설 명
노드의 모든 자식노드를 보유한 nodeList 콜렉션이다. 노드가 자식을 가지지 않더라도 nodeList는 리턴된다. 단지 childNode의 length가 0으로 설정될 뿐이다.

5) attributes

타 입
namedNodeMap노드
설 명
노드의 모든 자식노드를 보유한 namedNodeMap 콜렉션이다. 애트리뷰트 프로퍼티가 엘레멘트, 엔티티, 노테이션이 아닌 모든 노드에 대해서는 0으로 설정해 놓는다. 애트리뷰트를 가지지 않더라도 namedNodeMap은 리턴된다.


6) parentNode

타 입
node
설 명
노드의 부모노드를 지시하는 포인터다. nodeList콜렉션은 노드 바로 위에 있지만 parentNode는 nodeList 콜렉션 위의 노드를 가리킨다.

<html>
<script language="javascript" for="window" event="onload">
confirm(xml.documentElement.nodeName);
confirm(xml.documentElement.childNodes.item(0).parentNode.nodeName);
</script>
<xml id="xml">
<element1>
<element2/>
</element1>
</xml>
</html>


7) firstChild

타 입
node
설 명
노드의 첫번째 자식노드를 나타낸다. 자식이 없으면면 null로 설정된다.
myNode.firstChild 와 myNode.childNoeds.item(0)은 서로 같다.

8) lastChild

타 입
node
설 명
노드의 마지막 자식노드를 나타낸다. 자식이 없으면 null로 설정된다.
myNode.lastChild 와 myNode.childNoeds.item( myNode.childNoeds.length-1)은 서로 같다.

<html>
<script language="javascript" for="window" event="onload">
var myNode = xml.documentElement;
confirm(myNode.lastChild.nodeName);
confirm(myNode.childNodes.item(myNode.childNodes.length-1).nodeName);
</script>
<xml id = "xml">
<root>
<element1/>
<element2/>
<element3/>
</root>
</xml>
</html>


9) previousSibling

타 입
node
설 명
한 노드가 부모노드를 가지고 있고 그 부모의 자식이 현재노드 왼쪽에 있는 노드를 나타낸다. 만약에 이 자식노드가 존재하지 않는다면 null로 설정된다.

10) nextSibling

타 입
node
설 명
한 노드가 부모노드를 가지고 있고 그 부모의 자식이 현재노드 오른쪽에 있는 노드를 나타낸다. 만약에 이 자식노드가 존재하지 않는다면 null로 설정된다.

11) ownerDocument

타 입
document
설 명
현재 노드가 자리잡고 있는 DOM 트리의 Document 노드를 나타낸다. 노드를 생성할 수 있는 노드는 Document 노드이기 때문에 Document 노드로 쉽게 접근할 수 있는 방법으로 유용하다.

<HTML>

<BODY>

<script language=javascript for=window event="onload">

var myNode=xml.documentElement ;

confirm(xml.documentElement.nodeName);
confirm(xml.documentElement.nodeType);
confirm(xml.documentElement.childNodes.item(0).nodeValue);
confirm(xml.documentElement.childNodes.item(0).parentNode.nodeName);
confirm(xml.documentElement.childNodes.item(1).nodeName);
confirm(xml.documentElement.childNodes.item(1).parentNode.nodeName);
confirm(xml.documentElement.firstChild.nodeName);
confirm(xml.documentElement.childNodes.item(0).nextSibling.nodeName);
confirm(xml.documentElement.lastChild.nodeName);
confirm(xml.documentElement.childNodes.item(myNode.childNodes.length-1).previousSibling.nodeName);
confirm(xml.documentElement.childNodes.item(0).ownerDocument.nodeName);
confirm(xml.documentElement.childNodes.item(myNode.childNodes.length-1).childNodes.item(0).nodeValue);
</script>

<xml id = "xml">
<rootElement >
이글은 childNode입니다.
<subElement1 />
<subElement2 />
<subElement3 />
<lastElement>
에구구!
</lastElement>
</rootElement>
</xml>

</BODY>
</HTML>


(2) Node Methods

이제 부터 가술할 내용들은 주로 노드의 자식들을 관리하고 조작하기 위한 메소드들이다. 노드가 모두 다른 타입의 노드이기 때문에 비록 상속받은 메소드가 의미가 없더라도 따라오는 메소드는 상속을 받게 된다. 하지만 자식을 가질 수 없는 노드에게 자식에 영향을 미치는 메소드를 사용하면 에러가 발생하니 유의하자.

1) insertBefor(newChild,refChild)

인자
newChild와 refChild는 Node이다.
반환값
Node
예외처리
DOMException
설명
기존의 자식노드인 refChild앞에 newChild노드를 삽입한다.
만약 refChild가 null로 설정되면 자식리스트의 맨마지막에 삽입된다. refChild존재하지 않거나 newChild가 주어진 부모에 허용될 수 없다면 에러난다.

2) replaceChild(newChild,oldChild)

인자
newChild와 oldChild는 Node이다.
반환값
Node
예외처리
DOMException
설명
oldChild가 제거되고 newChild노드를 삽입한다.

3) removeChild(oldChild)

인자
oldChild는 Node이다.
반환값
Node
예외처리
DOMException
설명
oldChild가 제거된다.
만약 oldChild가 없으면 에러가 난다.

4) appendChild(newChild)

인자
newChild는 Node이다.
반환값
Node
예외처리
DOMException
설명
newChild를 맨마지막에 삽입한다.
만약 newChild가 트리 어딘가에 위치하여 있다면 먼저 그위치에서 제거된후 자식의 현재리스트에 덧붙여 진다.

<html>
<script language="javascript" for="window" event="onload">
var elem1 = xml.documentElement.childNodes.item(0);
var elem2 = xml.documentElement.childNodes.item(1);
confirm(xml.xml);
elem1.appendChild( elem2.childNodes.item(0) );
confirm(xml.xml);
</script>
<xml id = "xml">
<rootElement>
<elem1>
<childElement1/>
</elem1>
<elem2>
<childElement2/>
</elem2>
</rootElement>
</xml>
</html>

5) hasChildNode()

인자
none
반환값
boolean
예외처리
none
설명
자식노드가 있다면 true, 없으면 false값을 리턴한다.

6) cloneNode(deep)

인자
deep는 논리값이다.
반환값
Node
예외처리
none
설명
deep이 true이면 child를 가지고 복사한다.만약 deep이 거짓이면 노드가 복사되지만 자식들은 무시된다. true이면 자식노드를 모두 포함해서 복사된다.


//------------------------------------------------------------------------------






1. Document

(1) 부모노드

Document Node 노드의 부모노드는 Node이다. Document 노드는 그 밑에 있는 여러가지 노드를 다루는 도구를 포함하고 있다. 특히 Document노드가 나중에 트리에 삽입될 수 있는 노드를 생성하는데 이용된다. 또한 기본 검색처리방법도 포함되어 있고 rootElemet 노드와 DocumentType 노드같이 트리에 있는 중요한 노드에 대한 포인터도 가지고 있다.

(2) Document Propeties

1) documentElement

타 입
Element node
설 명
문서 내의 가장 높은 레벨의 Element를 나타낸다.


<HTML>

<BODY>

<script language=javascript for=window event="onload">
confirm(xml.documentElement.nodeName);
confirm(xml.documentElement.attributes.item(0).nodeName);
</script>
<xml id = "xml">
<엘레먼트이름 애트리뷰트이름 = "hello" />
</xml>
</BODY>
</HTML>


키워드 xml이 Document Node이고 xml.documentElement는 rootElement를 나타내는 Element 노드이다.
XML문서 전체를 나타내고 싶을때는 xml.xml을 이용한다.

2) docType

타 입
documentType Node
설 명
문서안의 DocumentType노드를 나타낸다. DTD내용의 일부를 포함하고 있다.

3) implementation

타 입
DOMimplementation Node
설 명
문서안의 DOMimplementation 노드를 나타낸다. 버전확인을 위한 매커니즘을 제공해 준다.



(2) Document Methods

1) createElement(tagName)

인자
tagName은 string이다.
반환값
Element
예외처리
none
설명
tagName에 맞추어진 nodeName 프로퍼티를 가진 Element 노드를 생성하고 리턴한다.

2) createDocumentFragment()

인자
none
반환값
DocumentFragment
예외처리
none
설명
새로운 DocumentFragment 노드를 생성한다.

3)createTextNode(data)

인자
data는 string 값이다.
반환값
Text Node
예외처리
none
설명
string data 를 포함하는 새로운 textNode를 생성한다.

4) createComment(data)

인자
data는 string 값이다.
반환값
Comment
예외처리
none
설명
string data 를 포함하는 새로운 Comment Node를 생성한다.

5) createCDATASection(data)

인자
data는 string 값이다.
반환값
CDATASection
예외처리
none
설명
string data 를 포함하는 새로운 CDATASection를 생성한다.

6) createProcessingInstruction(target,data)

인자
target과 data는 string 값이다.
반환값
ProcessingInstruction
예외처리
none
설명
새로운 ProcessingInstruction를 생성하고 반환한다. 주어진 파라미터 target과 data에 PI 프로퍼티인 target과 data를 설정한다.

7) createAttriute(name)

인자
name은 string이다.
반환값
Attriute
예외처리
none
설명
새로운 Attribute 노드를 생성하고 리턴한다. 그리고 name에 nodeName프로퍼티를 설정한다. nodeValue프로퍼티는 공백으로 남겨 놓는다.

8) createEntityReference(name)

인자
name은 string이다.
반환값
EntityReference
예외처리
none
설명
새로운 EntityReference 노드를 생성하고 리턴한다. 그리고 name에 nodeName프로퍼티를 설정한다.

9) getElementsByTagName(tagName)

인자
tagName은 string이다.
반환값
nodeList
예외처리
none
설명
파라미터 이름인 name에 부합되는 프로퍼티 tagName(또는 nodeName)을 가지는 Element 노드 리스트를 리턴한다. 이 메소드는 Document 노드에 속하는 모든 트리를 검색한다. 만약이 이름이 "*"와 같다면 모든 Element 노드가 리턴된다.


2. 트리관리의 예

(1) Node 생성

<html>
<script language="javascript" for="window" event="onload">
//새로운 element 노드를 생성한다.
var newNode = xml.createElement("element2");
//원하는 위치에 삽입한다.
xml.documentElement.insertBefore(newNode, null);
confirm(xml.xml);
</script>
<xml id = "xml">
<rootElement>
<element1/>
</rootElement>
</xml>
</html>

위의 예제는 새로운 엘리먼트를 어떻게 생성하고 트리에 그것을 어떻게 입력할 것인지를 보여 주고 았다. 위의 예제는 그냥 마지막에 삽입하기 위해 insertBefore(newNode, null)처럼 'null'을 지정해 주었다.

'xml.xml' 은 처음의 xml은 XML문서의 ID인 xml, 즉 문서 전체이고, 뒤의 xml은 마이크로소프트의 확장 프로퍼티인데 오직 MSXML에서만 사용되는 것이다.

(2) Node 삭제

<html>
<script language="javascript" for="window" event="onload">
//삭제할 노드를 찾는다.
var nodeToDelete = xml.documentElement.childNodes.item(1);
//노드를 삭제한다.
xml.documentElement.removeChild(nodeToDelete);
confirm(xml.xml);
</script>
<xml id = "xml">
<rootElement>
<element1/>
<element2/>
</rootElement>
</xml>
</html>

(3) Node의 이동

<html>
<script language="javascript" for="window" event="onload">
//이동을 할 노드를 찾는다.
var nodeToMove = xml.documentElement.childNodes.item(1);
//노드를 이동한다.
xml.documentElement.childNodes.item(0).appendChild(nodeToMove);
confirm(xml.xml);
</script>
<xml id = "xml">
<rootElement>
<element1/>
<element2/>
</rootElement>
</xml>
</html>


Node 클래스에 있는 appendChild(...)는 element2를 이동시키는데 사용되었다. remonveChild(..)와 InsertChild..(...) 를 함께 사용하면 같은 결과를 얻을 수 있을 것이다.

//------------------------------------------------------------------------------






1. Element

(1) 부모노드

Element Node 노드의 부모노드는 Node이다. 이 Element에만 존재하는 대부분의 메소드들은 애트리뷰트를 관리하는 메소드들이다.

(2) Element Propeties

1) tagName

타 입
string
설 명
Element의 태그이름을 나타낸다. Element에 대한 nodeName과 같다.

(2) Element Methods

1) getAttribute(name)

인자
name은 string 값이다.
반환값
string
예외처리
none
설명
name으로 명명된 애트리뷰트의 내용을 포함하는 문자열을 리턴한다.

2) setAttribute(name, value)

인자
name, value 는 string 값이다.
반환값
none
예외처리
none
설명
name으로 명명된 애트리뷰트가 존재하지 않는다면 name으로 명명된 문자열로 애트리뷰트를 만들고 그 값에 value를 준다. 만약 이미 존재하고 있다면 이전의 값을 새로운 값으로 대체된다.

3) removeAttribute(name)

인자
name은 string 값이다.
반환값
none
예외처리
none
설명
name으로 명명된 애트리뷰트를 삭제한다.

4) getAttributeNode(name)

인자
name은 string 값이다.
반환값
Attribute Node
예외처리
none
설명
name으로 명명된 애트리뷰트 노드를 리턴한다. 존재하지 않는다면 null을 리턴한다.
getAttribute(name) = getAttributeNode(name).nodeValue

5) removeAttributeNode(oldAttr)

인자
oldAttr은 Attribute Node이다.
반환값
none
예외처리
none
설명
oldAttr으로 명명된 애트리뷰트 노드를 제거하고 oldAttr를 리턴한다.

6) setAttributeNode(newAttr)

인자
newAttr은 Attribute Node이다.
반환값
none
예외처리
none
설명
newAttr는 Element Node의 Attribute 리스트에 추가된다. Attribute 노드는 Document 노드를 사용하여 생성할 수 있다. 또한 다른 Element에서 삭제되었던 Attribute가 이 메소드에 의해 사용될 수 있다.

<html>
<script language="javascript" for="window" event="onload">

var attrNode = xml.documentElement.getAttributeNode("myAttr");
xml.documentElement.removeAttributeNode(attrNode);
xml.documentElement.childNodes.item(0).setAttributeNode(attrNode);
confirm(xml.xml);
</script>
<xml id = "xml">
<rootElement myAttr="안녕하세요">
<myElem/>
</rootElement>
</xml>
</html>


7) getElementsByTagName(name)

인자
name은 string 값이다.
반환값
nodeList
예외처리
none
설명
파라미터 이름이 name에 부합되는 tagName을 가지는 Element Node의 리스트를 리턴한다. 이 메소드는 그것이 호출 받았던 element의 모든 하위 트리를 검색한다. 만약에 name이 "*"와 같다면 모든 엘리먼트 노드가 리턴된다. Document 노드 클래스의 메소드와 같은 일을 수행한다. 다만 Document 노드에서는 문서전체가 검색대상이고 Element에서는 지정된 Element의 하위트리만을 대상으로 한다.

8) normalize()

인자
none
반환값
none
예외처리
none
설명
인접한 Text노드를 한 노드로 합친다. 만약 프로그래머가 Text노드를 이동시킬때 서로 인접해 있기 때문에 쉽사리 이동이 가능한 형식으로 DOM문서를 만들었을때 부모노드에서 normalize()를 호출하면 인접한 두개의 Text Node가 합쳐지는 DOM문서를 만들 수 있다.

2. Element Node의 사용 예

(1) 자식노드 방문하기

childNode 콜렉션과 for loop를 이용하여 쉽게 작성이 가능하다. 좋은 반복구조 기능은 DOM 스펙에 첨가 되어 있다. 참조해 보기를 바란다. 여기서는 프로그램에서 메소드를 직접 호출하여 사용했다.

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">
<HTML><HEAD>
<META content="text/html; charset=ks_c_5601-1987" http-equiv=Content-Type>
<META content="MSHTML 5.00.2014.210" name=GENERATOR></HEAD>
<BODY onload=start()>
<SCRIPT language=javascript>

//엘리먼트 노드타입을 나타내기위해 전역변수(상수) 사용
var ELEMENT_NODE = 1;

function start() {
//탬색해야하는 자식들의 개수를 구한다.
var length = xml.documentElement.childNodes.length;

//개수만큼 반복
  for (index = 0; index < length; index++) {
    var childNode = xml.documentElement.childNodes.item(index);
// 자식이 엘리먼트인지 확인하여 참이면 태그이름출력
    if(childNode.nodeType == ELEMENT_NODE) {
      confirm(childNode.nodeName);
    }
  }
}

</SCRIPT>
<xml id=xml>
  <rootElement>
    <element1/>
    <element2/>
    <element3/>
  </rootElement>
</xml>
</BODY></HTML>


(2) Element의 내용보여주기

자식노드가 text 또는 CDATASection 노드라면 그 내용을 보연준다. 일단 모든 자식 노드를 방문하면서 Text Node 인지 CDATASection Node인지를 검사하여 참이면 내용을 보여주면 된다.

<html>
<body onload="start()">
<script language="javascript">

//nodeType 상수정의
var TEXT_NODE =3;
var CDATASECTION_NODE = 4;

//rootElement를 지정해 준다.
function start() {
   displayContents(xml.documentElement);
}

//모든 노드를 방문하면서 Text와 CDATASection의 내용을 보여준다.
function displayContents(node) {
   var length = node.childNodes.length;
   var index;
   var outputBuffer = ""; //출력하기 위한 버퍼

   for (index = 0; index < length; index++) {
      var childNode = node.childNodes.item(index);
      if (childNode.nodeType == TEXT_NODE) {
         outputBuffer += childNode.nodeValue;
      }
      if (childNode.nodeType == CDATASECTION_NODE) {
         outputBuffer += childNode.nodeValue;
      }
   }
   confirm(outputBuffer);
}

</script>
</body>
<xml id = "xml">
<rootElement>
지금 텍스트를 시작합니다...

<![CDATA[<B>굵은 글자체로 쓰겠습니다.</B>]]>

이제 텍스트를 끝냅니다...
</rootElement>
</xml>
</html>


(3) 트리에 있는 모든 노드 방문하기

자료구조내의 트리의 운행방법중 하나인 "깊이 우선 검색법 : 형제노드를 방문하기전에 자식노드를 먼저 방문하는 방법"을 선택하여 모든 노드를 방문하고자 한다. 이때 사용하는 방법은 재귀호출을 이용한다. 여기서는 프로그래밍 구조를 살펴보기 위하여 노드를 엘리먼트만을 처리했다. 애트리뷰트가 있어 그것도 탐색하고 싶다면 애트리뷰트가 았는지 확인하고 있으면 애트리뷰트 탐색하는 부분을 추가하면 가능할 것이다.

<html>
<body onload="start()">
<script language="javascript">

var ELEMENT_NODE = 1;

//루트엘리먼트로 함수 시작
function start() {
   visit(xml.documentElement);
}

//노드방문함수
function visit(node) {
   //엘리먼트인지 확인-맞으면 엘리먼트 출력
   if(node.nodeType == ELEMENT_NODE) {
      confirm(node.nodeName);
      // 이때 str += nodeNmae 같이 태그이름을 문자열로 만들 수도 있다.
   }
   //자식 노드의 개수를 가져온다.
   var length = node.childNodes.length;
   // 자식 노드가 있다면 자식 노드의 개수만큼 노드를 탐색한다.
   if (length > 0) {
      var index;

      for (index =0; index < length; index++) {
         // 노드 방문함수를 이용하여 재귀호출하여 계속 진행된다.
         visit( node.childNodes.item(index));
      }
   }
}

</script>
</body>
<xml id = "xml">
   <rootElement>
      <element1>
         <childElement1/>
      </element1>
      <element2/>
      <element3>
         <childElement2/>
      </element3>
   </rootElement>
</xml>
</html>


(4) Attribute의 관리방법

<html>
<body onload="start()">
<script language="javascript">

function start() {
var rootElement = xml.documentElement;

rootElement.setAttribute('myAttr', '반갑습니다.');
alert(rootElement.getAttribute('myAttr'));
}

</script>
</body>
<xml id = "xml">
<rootElement/>
</xml>
</html>


//------------------------------------------------------------------------------






1. Attribute

(1) 부모노드

부모노드는 Node이다. Element, Entity, Notation 내의 애트리뷰트를 관리한다. 프로퍼티와 메소드가 많지는 않지만 몆가지라도 알아두면 쓰임새가 있다. Attribute노드는 실제로 Attr로 정의된다.

(2) Attribute Propeties


1) name

타 입
string
설 명
Attribute 노드의 이름을 나타낸다. Node로 부터 상속박은 nodeName과 같다.

2) specified

타 입
Element 논리값
설 명
Attribute 가 파서에 의해 로드되기전에 XML문서에 기입된다면 true로 설정된다.

3) value

타 입
string
설 명
Attribute 노드의 값을 나타낸다. Node로 부터 상속박은 nodeValue과 같다.

2. NodeList

(1) 부모노드

부모노드는 없다. DOM 트리를 검색하는데 있어서 결정적인 역할을 하는 요소이다.

(2) NodeList Propeties


1) length

타 입
unsigned long integer
설 명
NodeList안에 있는 자식의 개수를 리턴한다.

(2) NodeList Methods

1) item(index)

인자
index는 unsigned long integer 값이다.
반환값
node
예외처리
none
설명
NodeList가 관리하는 자식들중에 index값에 해당하는 노드을 리턴한다.
첫번째 자식 : index = 0
마지막 자식 : index = length -1
IE5.0 이상에서는 somenode.childNodes(index)를 사용할 수 있다.

2. NamedNodeMap

(1) 부모노드

부모노드는 없다. 애트리뷰트 콜렉션을 유지하기 위해 사용된다.

(2) NamedNodeMap Propeties


1) length

타 입
unsigned long integer
설 명
NamedNodeMap안에 있는 자식의 개수를 리턴한다.

(2) NamedNodeMap Methods

1) item(index)

인자
index는 unsigned long integer 값이다.
반환값
node
예외처리
none
설명
NamedNodeMap가 관리하는 자식들중에 index값에 해당하는 노드을 리턴한다.
첫번째 자식 : index = 0
마지막 자식 : index = length -1

2) getNmaedItem(name)

인자
name은 string 값이다.
반환값
node
예외처리
none
설명

name과 같은 nodeName 프로퍼티를 가지는 노드를 리턴한다 . 만약 없으면 null을 리턴한다.


3) setNmaedItem(node)

인자
node는 Node이다.
반환값
node
예외처리
DOMException
설명
node와 함께 지정된 노드를 트리에 더하고 node를 리턴한다. 만약 같은 이름의 node가 존재한다면 node로 치환되고 옛날 노드는 리턴된다.
다음 3가지중에 한가지라도 걸리면 예외상황이 발생한다.
1) node가 다른문서 안에서 생성된 경우
2) NamedNodeMap이 read-only인경우
3) node가 현재 다른 앨리먼트내에 있는 애트리뷰트인 경우
단, IE5.0이상에서는 Document에서 createAttribute로 생성한 노드를 예외상황없이 다른 Document 노드의 트리에 입력할 수 있다.

4) removeNmaedItem(name)

인자
name은 string 값이다.
반환값
node
예외처리
DOMException
설명

name과 같은 nodeName을 가지는 노드를 삭제하고 노드를 리턴한다 . 만약 처음부터 노드가 없으면 null을 리턴하고 지정된 노드가 없다면 예외상황이 발생한다.
단, IE5.0이상에서는 노드가 없더라도 예외상황이 발생되지 않는다.


3. CharacterData

(1) 부모노드

부모노드는 Node 이다. Text, CDATASection, Comment 노드에 의해 사용되어 진다. 때문에 string을 다루기 위한 프로퍼티와 메소드가 제공된다.

(2) CharacterData Propeties

1) length

타 입
integer
설 명
text string의 글자 수를 리턴한다.

2) data

타 입
string
설 명
CharaterData로부터 상속받은 노드에 저장된 text를 리턴한다.
nodeValue와 같은 값을 리턴한다.

(2) CharacterData Methods

1) substringData(offset,count)

인자
offset,count는 unsigned long integer 값이다.
반환값
string
예외처리
DOMEception
설명
offset에서 시작하는 문자열로부터 count만큼의 문자를 리턴한다.
offset,count가 정당하지 않다면 에러를 낸다.
offset은 양의 정수값을 가진다. 또한 전체길이(length)를 초과할 수 없다.
offset을 0으로 설정하는 것과 count를 length로 설정한다는 것은 string 전체를 리턴한다.

2) appendData(appendString)

인자
appendString은 string 값이다.
반환값
node
예외처리
DOMEception
설명

기존의 텍스트에 appendString을 덧붙인다.
노드가 read-only면 에러가 난다.


3) insertData(offset, newString)

인자
offset은 unsigned long integer, newString은 string이다.
반환값
node
예외처리
DOMException
설명
offset에 위치한 기존의 텍스트에 newString을 삽입한다.
offset이 정당하지 않거나 read-only면 에러가 발생한다.

4) deleteData(offset,count)

인자
offset,count는 unsigned long integer 값이다.
반환값
none
예외처리
DOMException
설명

기존의 텍스트에서 offset에서 시작하는 텍스트 스트링으로부터 count만큼 문자를 제거한다.
offset이 정당하지 않거나 read-only면 에러가 발생한다.


4) replaceData(offset, count, data)

인자
offset,count는 unsigned long integer, data는 string이다.
반환값
none
예외처리
DOMException
설명

기존의 텍스트에서 offset에서 시작하는 텍스트 스트링으로부터 count만큼 문자를 data로 치환한다.
offset이 정당하지 않거나 read-only면 에러가 발생한다.


4. Text

(1) 부모노드

부모노드는 characterData이다.

(2) Text Methods


1) splitText(offset)

인자
offset은 long integer 이다.
반환값
none
예외처리
none
설명

호출된 텍스트를 두개의 텍스트로 만든다. 첫번째는 offset의 위치를 포함 텍스트이고, 두번째 텍스트는 offset 이후의 모든 텍스트이다.


5. CDATASection

(1) 부모노드

부모노드는 Text 이다. Text 노드와 비슷하게 행동하지만 단하나의 차이는 CDATA 부분이 그안에 저장될 수 있다.

6. DocumentType

(1) 부모노드

부모노드는 Node이다. DTD를 나타내는데 사용한다. 다만 Entity와 Notation만 나타낸다. 모든 프로퍼티가 read-only 이다.

(2) DocumentType Propeties

1) name

타 입
string
설 명
DOCTYPE 바로 다음에 아노는 이름을 나타내며 바로 root element의 이름이다.

2) entities

타 입
namedNodeMap
설 명
이 문서에 대한 Entiy 콜렉션을 나타낸다.
각 Entity 노드는 DTD에 있는 엔티티선언을 모델화한 것이다.

3) notations

타 입
namedNodeMap
설 명
이 문서에 대한 Notation 콜렉션을 나타낸다.
각 Notation노드는 DTD에 있는 notation 선언을 모델화한 것이다.

7. Entity

(1) 부모노드

부모노드는 Node이다. DTD에 선언된 entity 를 모델화한 것이다. DOM 트리에서는 entity 노드가 DocumentType 노드 아래에서만 사용된다.

(2) Entity Propeties

1) systemId

타 입
string
설 명
엔티티와 관련된 시스템식별자를 나타낸다. 없다면 null이다.

2) publicId

타 입
string
설 명
엔티티와 관련된 공개된 식별자를 나타낸다. 없다면 null이다.

3) notationName

타 입
string
설 명
파서되지 않은 엔티티에 대한 notation 이름을 나타낸다. 파서된 엔티티뿐이라면 null을 나타낸다.

8. Notation

(1) 부모노드

부모노드는 Node이다. DTD에 선언된 notation을 모델화한 것이다. DOM 트리에서는Notation 노드가 DocumentType 노드 아래에서만 사용된다.

(2) Notation Propeties

1) systemId

타 입
string
설 명
Notation과 관련된 시스템식별자를 나타낸다. 없다면 null이다.

2) publicId

타 입
string
설 명
Notation과 관련된 공개된 식별자를 나타낸다. 없다면 null이다.

9. EntityReference

(1) 부모노드

부모노드는 Node 이다. EntityReference 노드는 대응하는 Entity 노드를 가리키는데 사용된다. 이 노드 타입은 그 자신의 프로퍼티와 메소드의 어떤것도 확장시키 않는다. 때문에 단지 Node안에 선언된 메소드와 프로퍼티만 EntityReference와 함께 사용할 수 있다. EntityReference 아래에 있는 노드는 read-only 이다. EntityReference 노드는 하위트리 전체를 포함해서 다수의 노드를 포함하는데 사용되어질 수 있다.

10. ProcessingInstruction

(1) 부모노드

부모노드는 Node이다. ProcessingInstruction 노드는 XML문서내의 processingInstruction을 나타내는데 사용된다.

(2) ProcessingInstruction Propeties

1) target

타 입
string
설 명
<?target text?>의 형식으로 존재하는 PI의 표적을 나타낸다.

2) data

타 입
string
설 명
<?target text?>의 형식으로 존재하는 PI의 텍스트를 나타낸다.

11. Comment

(1) 부모노드

부모노드는 CharacterData 이다. Comment 노드는 XML문서안의 <!-- text -->와 같은 주석을 나타내는데 사용된다. 이 노드는 Text와 비슷하게 동작한다. 왜냐하면 주석내 텍스트을 사용할 수 있기 때문이다.

12. DocumentFragment

(1) 부모노드

부모노드는 Node 이다.

DocumentFragment 노드는 어떠한 XML문서를 나타내지 않는다. 대신에 노드를 이동시칼때 위치소유자(place holder)로서 사용된다. DocumentFragment 노드를 어떤 노드(Document나 Element)의 자식 리스트에 입력할때 오직 DocumentFragment의 자식들과 DocumentFragment 그 자신만이 입력된다. DocumentFragment는 트리안에 존재하는 Element를 합치는데 유용하게 사용된다. 일단 DocumentFragment에서 Element 콜렉션을 생성하면 자식들은 하위트리로 이동된다.

간단한 예를 한번 보도록 하자.

<html>
<body onload="start()">
<script language="javascript">
function start() {
// DocumentFragment 노드를 생성한다.
  var myDocFrag = xml.createDocumentFragment();

// 두개의 Element 노드를 생성한다.
  var element1 = xml.createElement("element1");
  var element2 = xml.createElement("element2");

// 생성된 두개의 Element 노드를 DocumentFragment 노드에 자식으로 삽입한다.
  myDocFrag.insertBefore(element1, null);
  myDocFrag.insertBefore(element2, null);

//실제 xml의 root엘리먼트에 DocumentFragment에서 생성된 트리를 삽입한다.
  xml.documentElement.insertBefore(myDocFrag, null);

  confirm(xml.xml);
}

</script>
</body>
<xml id = "xml">
  <rootElement/>
</xml>
</html>


기본 로직은 대충 이해될 것이다. 다만 유의해서 봐야 할 것은 결과를 살펴볼 때 DocumentFragment를 사용했다는 어떠한 흔적도 증거도 남아있지 않다는 것이다. 즉 서로 다른곳에 위치한 필요한 트리를 DocumentFragment의 하위트리에 모아 놓고 한꺼번에 삽입시킬 수 있다는 것이다.

13. DOMImplemetation

(1) 부모노드

부모노드는 없다. DOMImplemetation 클래스는 DOM의 어느 특정 인스턴스와는 독립적으로 세세한 구현을 하기 위해 사용된다.

(2) DOMImplemetation Methods

1) hasFeature(feature, version)

이 메소드는 마크업언어와 버전을 받아서 참 또는 거짓을 리턴한다. 특정 버전은 특정한 마크업언어에 의존하는 것이 있다. 때문에 버전을 확인하는 것이 중요할 때가 있을 것이다. 그때 사용하면 된다.

14. DOMString

(1) 부모노드

부모노드는 없다. DOMString의 단 하나의 요구조건은 UTF-16 인코딩을 사용한다는 것이다. 실제 많이 사용되지 않는다. 왜냐하면 애플리케이션의 string을 그대로 많이 사용하기 때문이다.

15. DOMException

(1) 부모노드

부모노드는 없다. 언어 의존적인 존재이기 때문에 Java나 .NET에서나 가능할 것이다.

//------------------------------------------------------------------------------






DOM (계속)

원하는 노드 찾아가기

  • Node 객체의 운행(Traversal) 관련 속성
    • 관련속성
    • hasChildNodes() 메소드
  • NodeList 객체 
    • 노드들의 리스트, 예: childNodes 객체
    • length 속성, item(번호) 메소드
      xdoc.load("ex08.xml");
     var xroot = xdoc.documentElement;
     if (xroot.hasChildNodes) {
         alert(xroot.childNodes.length);
         var curr = xroot.firstChild;  alert(
    curr.ownerDocument.nodeName + curr.xml);
         alert(curr.nodeName + curr.nodeTypeString + curr.nodeValue + curr.attributes.length);
     }
     else alert('No Child');  
      xdoc.load("ex08.xml");
     var xroot = xdoc.documentElement;
     var curr = xroot.firstChild.nextSibling;    alert(curr.xml);
     curr = curr.childNodes.item(2);    alert(curr.xml);
     curr = cur.previousSibling;    alert(curr.text);
     alert(curr.nodeName + curr.nodeTypeString + curr.nodeValue + curr.attributes.length);

임의 노드의 검색

  • Document 객체에서 태그 이름으로 검색
    • 노드리스트 = 문서.getElementsByTagName("tagName");
       xdoc.load("ex08.xml");
     var nlist = xdoc.
    getElementsByTagName("book");
     for (i=0; i<nlist.length; i++) alert(nlist.item(i).xml);
      xdoc.load("ex08.xml");
     var nlist = xdoc.
    getElementsByTagName("title");
     for (i=0; i<nlist.length; i++) alert(nlist.item(i).xml);
      xdoc.load("ex08.xml");
     var nlist = xdoc.
    getElementsByTagName("author");
     var result = "";
     for (i=0; i<nlist.length; i++) result = result + nlist.item(i).xml + "\n";
     alert(result);
  • Node객체에서 패턴으로 검색
    • 노드리스트 = 노드.selectNodes("pattern");
    • 노드 = 노드.selectSingleNode("pattern");
      xdoc.load("ex08.xml");
     var xroot = xdoc.documentElement;
     var node1 = xroot.selectSingleNode("title");    alert(node1.text);
     var tlist = xroot.selectNodes('//title');
     var alist = xroot.selectNodes('//author');
     for (i=0; i<alist.length; i++)  
        alert('[' + i + '] ' + alist.item(i).text + ', ' + tlist.item(i).text);

      xdoc.load("ex08.xml");
     var xroot = xdoc.documentElement;
     var node1 = xroot.selectSingleNode('//book[@InStock=0]');
     alert(node1.xml+'\n=> 재고가 없습니다.');
     var tlist = xroot.selectNodes('//book[@InStock!=0]/title');
     var result="";
     for (i=0; i<tlist.length; i++) result = result + tlist.item(i).text + "\n";
     alert("재고 있음 =>\n" + result);

실습예제 : 도서 검색 (교재 s20-05.htm 응용)

    XML 파일 경로 입력 또는 '찾아보기'로 선택

    'LOAD'로 파일을 메모리에 로드 :
      또는
    기본 예제 파일 (서점 도서 목록) 이용하기 :

    원하는 검색 조건을 입력하고 '검색' 버튼 클릭

    1) 엘리먼트 또는 속성 이름 검색 :    
    2) '텍스트 내용' 또는 속성값 검색 : 
     
       
    3) 조건검색 {이름, 비교, '내용'/값}
     
     

    <div id="resDiv">검색 결과</div>

    1) ... :<INPUT type="text" name="cond0" size="25">&nbsp;
    <INPUT type=button value="검색" onclick="
            var resHTML='';
            var nlist = xmldoc.getElementsByTagName(cond0.value);
                   
            for (var i=0; i&lt;nlist.length; i++) resHTML += nlist(i).xml + '\n\n';
            if (resHTML)                    
                  resDiv.innerText = resHTML;
            else
                  resDiv.innerHTML = '<H3>No match found by this search</H3>';  
           ">

    2) ... : <INPUT  type="text" name=cond1 size="25">&nbsp;
    <INPUT type=button value="검색" onclick="
            var resHTML='';
            var xroot = xmldoc.documentElement;
            var nlist = xroot.selectNodes('//*[text()=' + cond1.value + ']');
            var alist = xroot.selectNodes('//@*[text()=' + cond1.value + ']');
                   
            for (var i=0; i&lt;nlist.length; i++)  resHTML += nlist(i).xml + '\n\n';
            for (var i=0; i&lt;alist.length; i++)  resHTML += alist(i).xml + '\n\n';
            if (resHTML)                    
                   resDiv.innerText = resHTML;
            else
                   resDiv.innerHTML = '<H3>No match found by this search</H3>' ;
            ">

    3) ... : <INPUT  type="text" name=con21 size="12">&nbsp; <select name="comp"><option value="=">=...</select><INPUT  type="text" name=con22 size="12">
    <INPUT type=button value="검색" onclick="
            var resHTML='';
            var xroot = xmldoc.documentElement;
            var nlist = xroot.selectNodes('//'+con21.value+'[text()'+comp.value+con22.value+']');
                   
            for (var i=0; i&lt;nlist.length; i++)  resHTML += nlist(i).xml + '\n\n';
            if (resHTML)                    
                   resDiv.innerText = resHTML;
            else
                   resDiv.innerHTML = '<H3>No match found by this search</H3>';
            ">

 문서에 새로운 노드 추가하기

  1단계. 문서객체 내에 신규 노드 만들기
    ① [신규 생성] 엘리먼트노드 = 문서.createElement(“태그이름”)
    ② [신규 생성] 데이터노드 = 문서.createTextNode(“노드값”)
    ③ [데이터 붙이기] 엘리먼트노드.appendChild(데이터노드)

2단계. 원하는 노드 밑에 붙이기    a) [원하는 위치에] 부모노드.appendChild(신규노드)
                        또는  부모노드.insertBefore(신규노드, 기존노드)
    b) [새문서, 특수노드의 경우] 문서.appendChild(신규노드)
                                        또는  문서.insertBefore(신규노드, 기존노드)

           

 

  • Document 객체에 노드 신규생성 메소드
    • createElement(name), createAttribute(name), 
    • createTextNode(data), createCDATASection(data), 
    • createComment(data), createProcessingInstruction(target,data), ...
     xdoc.async = false;
     xdoc.loadXML( "<book> <title> XML 입문 </title> <author> 일지매 </author> </book>");
     elmt = xdoc.createElement("pages");  alert(elmt.xml);
     pg = xdoc.createTextNode("386");  alert(pg.xml);  
     stock = xdoc.createAttribute("Instock");  alert(stock.xml);

     cmt = xdoc.createComment("노드추가");
     pi = xdoc.create
    ProcessingInstruction("xml-stylesheet",  "type='text/xsl' href='ex8.xsl'");  
     cd = xdoc.createCDATASection("<1>");  alert(cd.xml);
     alert(xdoc.xml);
  • 노드의 추가 (Node, Document 객체 메소드)
    • appendChild(child)
    • insertBefore(child,before)
     xdoc.loadXML( "<book> <title> XML 입문 </title> <author> 일지매 </author> </book>");
     elmt = xdoc.createElement("pages");  
    // (1)
     pg = xdoc.createTextNode("386");  // (2)
     elmt.appendChild(pg);  alert(elmt.xml +'\n----------\n' + xdoc.xml);  
    // (3)
     xroot = xdoc.documentElement;
     xroot.appendChild(elmt);
     alert(xdoc.xml);  
    // (a)
     xdoc.loadXML( "<book>  ... </book>");
     cmt = xdoc.createComment("노드추가");  
    // (1)
     xdoc.appendChild(cmt);  alert(xdoc.xml);    // 문서에 노드 연결 (b)
     xroot = xdoc.documentElement;  alert('[PI 삽입전 root] : '+xroot.nodeName);
     pi = xdoc.createProcessingInstruction("xml-stylesheet", "type='text/xsl' href='ex7.xsl'");  
    // (1)
     xdoc.insertBefore(pi,xroot);  alert('[PI 삽입후] : '+xmldoc.xml); 
    // 문서에 노드 연결 (b)
     xroot = xdoc.documentElement;  alert('[PI 삽입후 root] : '+xroot.nodeName);
  • 중간에 노드 삽입할 때 주의
           
     cmt = xdoc.createComment("노드추가");
     xdoc.insertBefore(cmt, xdoc.firstChild);    alert('[xdoc] :\n'+xdoc.xml);
     
    xroot = xdoc.documentElement;      alert('[root] : '+xroot.nodeName);
     elmt = xdoc.createElement('list');    // (1)
     elmt.appendChild(xroot);      alert('[elmt] :\n\n'+elmt.xml);    // (2)
     xdoc.documentElement = elmt;     alert('[xdoc] :\n\n'+xdoc.xml);    // (3)

노드의 삭제/수정 (Node, Document 객체 메소드)

  • removeChild(child), replaceChild(child,toReplace)
     
        원하는 경우:
     xdoc.loadXML( "<book> <title> XML 입문 </title> <author> 일지매 </author> </book>");
     xroot = xdoc.documentElement;
     elmt = xroot.firstChild;  node=elmt.removeChild(elmt);
         alert('[삭제] :\n\n'+node.nodeValue); alert('[결과] :\n\n'+xdoc.xml);
     elmt = xroot.lastChild;  node=xroot.removeChild(elmt);
         alert('[삭제] :\n\n'+node.xml); alert('[결과] :\n\n'+xdoc.xml);
     

속성 읽어오기

  • NamedNodeMap 객체 
    • 이름="값"의 쌍으로 구성된 객체의 모임, 순서 상관 없음
    • getNamedItem("속성명"), setNamedItem(속성노드), removeNamedItem("속성명") 메소드
  • Attribute 노드 객체
    • getAttributeNode(“속성명”), setAttributeNode(속성노드), removeAttributeNode(속성노드)
  • Element 노드 객체
    • getAttribute(“속성명”), setAttribute(“속성명”, “속성값”), removeAttribute(“속성명”)
     xdoc.load("ex08.xml");
     var xroot = xdoc.documentElement;        

     var attrs = xroot.firstChild.attributes;
     var attr0 = attrs.getNamedItem("InStock");          // name ,  value 와  동일한 결과
     
    alert('[getNamedItem] : ' + attr0.xml + '\n' + attr0.nodeName + attr0.nodeValue);

     var xroot=xdoc.documentElement;          
     var attr0 = xroot.firstChild.getAttributeNode('InStock');
     alert('[getAttributeNode] : ' + attr0.xml+ '\n' + attr0.name + attr0.value);

     var xroot=xdoc.documentElement;          
     var attr = xroot.firstChild.getAttribute('InStock');
     alert('[getAttribute] :'+ attr + '\n' + attr.name + attr.value);

새로운 속성 추가하기

  A. 속성 노드 만들어서 붙이기
    ① [신규생성] 속성노드 = 문서.createAttribute(“속성명”)
    ② [속성값 설정] 속성노드.nodeValue = “속성값”
    ③ [속성 추가] 해당노드.attributes.setNamedItem(속성노드)
               [또는] 해당노드.setAttributeNode(속성노드)

B. 속성값 설정하기
     
해당 노드.setAttribute(“속성명”, “속성값”)

           

 
 

속성의 수정/삭제

  • nodeName, nodeValue, nodeType 등 속성 (name, value, type 동일)
  • NamedNodeMap 객체 :
    • getNamedItem("속성명"), setNamedItem(속성노드), removeNamedItem("속성명")
     xdoc.loadXML( "<book> ... </book>");
     elmt = xdoc.createElement('price');
     cur = xdoc.createAttribute('currency');  alert(cur.xml);  
      // (1)
     elmt.attributes.setNamedItem(cur);  alert(elmt.xml);    
    // (3)
     cur.nodeValue = 'won';  elmt.text = '33000';   alert(elmt.xml);    
    // (2)
     stock = xdoc.createAttribute('InStock');  stock.value=7;   alert(stock.xml);  
    // (1), (2)
     xroot = xdoc.documentElement;  xroot.appendChild(elmt);
     xroot.attributes.setNamedItem(stock);  alert(xdoc.xml);    
    // (3)
     
  • Element 노드 : 
    • getAttribute(“속성명”), setAttribute(“속성명”, “속성값”), removeAttribute(“속성명”)
     xdoc.loadXML( "<book> ... </book>");
     elmt = xdoc.createElement('price');
     elmt.setAttribute('currency','won');  elmt.text = '33000';   alert(elmt.xml);  
    // 신규속성 추가
     xroot = xdoc.documentElement;  xroot.appendChild(elmt);
     xroot.setAttribute('InStock','7');  alert(xdoc.xml);      
    // 신규속성 추가
     st1 = xroot.getAttribute('InStock');
     st2 = xroot.attributes.getNamedItem('InStock');
     alert('[1] '+st1+'\n[2] '+st2.xml);
     xroot.setAttribute('InStock','9');  alert(xroot.xml);      
    // 속성값 변경
     xroot.removeAttribute('InStock');  alert(xdoc.xml); 

*문서의 변환*

  • transformNode(스타일시트)

    <HTML>
      ...
      <xml  id="xdoc"> </xml>
      <xml  id="xsldoc"> </xsl>
      ...
    </HTML>
     

     xdoc.async = false;
     
    xdoc.load('ex08.xml'); alert(xdoc.xml);
     xsldoc.async = false;
     
    xsldoc.load('ex08.xsl'); alert(xsldoc.xml);
     var newdoc = xdoc.transformNode(xsldoc.XMLDocument);
     alert(newdoc);
     
    var anwin = window.open('', ' ', 'width=500, height=400');
     anwin.document.write(newdoc);

      ">
     alert(newdoc);
     result.innerHTML=newdoc;

     
     result.innerText=" ... "

    <div id="result"> ... </div>
     

//------------------------------------------------------------------------------

신고

'소프트웨어 > XML' 카테고리의 다른 글

XML 기본 내용  (2) 2007.07.10
MSXML 4.0/5.0 대신 MSXML 3.0/6.0 을 사용해야 하는 이유~  (0) 2006.12.30
Trackback 1 Comment 2
  1. BlogIcon 완전초보 2007.07.11 17:20 신고 address edit & del reply

    글 오른쪽이 잘린 부분이 많아서 그러는데
    원문 주소 좀 알 수 있을까요?
    출처가 안나와있네요;;;

  2. BlogIcon falconer 2007.07.12 09:02 신고 address edit & del reply

    출처을 정확하게 몰라서 올려 놓치 않았어요.
    위 내용을 그냥 카피 하시고 MS Word같은 곳에 붙여 놓고 하시면
    정상적으로 다 볼수 있을 것 같네요.

    ^^;

2007.06.28 08:59

Web 2.0 Machine is using us 한국자막

지난 웹앱스콘 인트로에 보여 드렸던 Web 2.0 Machine is using us의 한국어 자막 버전을 요청하시는 분들이 계셔서 동영상으로 다시 제공 합니다. 본 동영상은 캔사스 주립대의 디지털 인류학 연구실에서 만든 동영상으로 디지털 텍스트의 멋진 진화와 사람을 연결하는 웹2.0의 본질에 대해 잘 이야기 해주는 동영상입니다.



이미 많은 분들이 이 동영상을 보셨을 거구요. 한국어 자막은 약간 의역을 통해 만든 것입니다.







출처 : 챠니
신고
Trackback 0 Comment 0
2007.04.11 19:01

Five Ajax Anti Pattern

http://www-128.ibm.com/developerworks/web/library/x-ajaxxml3/index.html 에 있는 글을 간단히 정리했다. 제목은 “Ajax에서 사용하면 안될 패턴 5가지” 쯤 될 것 같다. 설명은 이해하기 쉽도록 따로 달았지만, 해당 코드와 함께 보려면 원래 글을 읽어볼 것을 권장한다.

#불필요한 타이머  사용
window.setInterval()  코드를 사용할 때 주의하라. 위 링크에 간단한 예제가 있는데, setInterval 은 내가 실행한 코드의 실행이 완료되었느냐에 상관없이 무조건 실행해버린다. 간격을 1초라고 정했는데, 어떤 이유로 코드 실행이 0.5초, 2초, 0.6초가 걸렸다고 하면…. 결과는 정말로 내가 원했던 그것일까?

# 콜백에서 반환 결과를  체크하지 않는 것
XHR이 항상 올바른 결과를 반환할 것이라고 생각한다면 큰 오산! 반드시 체크해야 한다(관련 내용을 제공하는 프레임웍을 사용중이라면 생략해도 무방)

# HTML이 더 좋은 방법인데도 XML을 고집한다
“난 순수하니까 HTML을 사용하지 않겠어”라는 생각은 금물. 때로는 XML을 파싱하고 가공하는 것보다 HTML과 innerHTML을 다루는 것이 훨씬 더 간단할 수도 있다.

# JSON을 사용할 일을 XML로 고집한다
어차피 JavaScript로 가공할 거라면 XML보다 JSON이 더 좋다. eval() 한번이면 텍스트가 금새 JavaScript 데이터로 변환된다. 영리한 개발자들은 이미 XML대신 JSON을 많이 사용하고 있다.(원문에는 JSON대신 Javascript code라는 표현으로 나와있었음)

# 서버에서 심각하게 많은 작업을 처리한다
밸런싱의 문제는 항상 있는 것이긴 하지만, 서버에 너무 많은 부담을 지우지는 말자.


덧글
  공대여자   07-04-08 02:49  
간단채팅에서 왜 JSON안쓰냐고 막 따지시는 분이 계시던데,
XML이 나쁜게 아닙니다. 개발자가 XML을 더 익숙하게 다루거나,
JavaScript 만 사용하는게 아니라면 XML로 만드는게 훨씬좋죠.
(물론 처리 속도 같은건 따로 생각하고.)
실제 간단 채팅은 UI를 FLASH로도 만들었는데...
(뭐 이야기 할때는 아직 안만들었지만, 만들꺼라고 말해도...)
     
   행복한고니   07-04-08 03:17  
JSON을 안 썼다고 따질만한 사항은 아니지만.. (만드는 사람 마음인데 뭐...)

JavaScript만 사용하는게 아니라고 해서 XML이 훨씬 좋다는 이유는 잘 모르겠습니다.
사용해보면 "JavaScript와 함께 이용하는 단순한 데이터" 에는 JSON 만큼 편한게 없는 것 같더군요.

XML도 물론 장점이 있습니다만, DTD를 통한 엄격한 구조 체크, XSLT와의 연동, 다양한 결과물 산출, 보다 복잡한 데이터 형태 구성 등등의 장점이 필요하지 않다면 XML로 만드는 것보다는 JSON 형태가 더 간단하고 데이터의 양이 1byte라도 줄기 때문에 더 좋습니다.

또한 대중적인 언어에는 이미 JSON 라이브러리가 있습니다. Flash를 비롯, C, Java, PHP 등등 다 있으니 XML의 큰 장점인 "호환성" 역시 JSON이 뒤쳐지진 않습니다. 덧붙여서 JSON에서는 XML에서 표현하기 힘든 Number 타입도 표현이 가능하죠. :)
          
   명랑폐인   07-04-08 16:14  
XML이 초기 기대했던것보다 그 역활이 크게 늘지 않았다고 합니다. xml 은 실제로 사람보다는 기계(머신)이 이해하기 편한 언어입니다. xml 보다는 json이 사람이 보기에 편하죠.
xml로 된 설정파일들 보면 골이 아파 옵니다. j2ee에서도 어노테이션을 통해서 xml 파일은 자동 생성 변환되는 형태로 가고 있구요.(그만큼 xml은 사람이 이해해서 자유자재로 쓸만한 언어는 아니라는 거겠죠.)

프로그래밍 하는 입장에서 사람이 이해하기 편한게 좋은것 같습니다.
               
   낭망백수   07-04-08 19:34  
저는 XML 이 보기에 더 편하더군요.
JSP 때문에 첨 XML 을 실무적으로 다루기 시작하였고,
SOAP 때문에 WSDL 찬찬히 살펴보게 되면서...
이젠 자바 빌드때문에 ANT에 관심갖다보니
XML 이 훨씬 다양한 내용에 대해 일맥상통한 폼을 갖고 있다는 것에 감사하곤 합니다.

뭘 담고 있느냐 혹은 어디에 익숙하느냐에 따라서 다를 것 같다는 말씀이죠.

역시, JSON 의 강점은 Javascript 에서 바로 사용할 수 있다... 정도일 듯 합니다.

행복한고니//
요약해 주신 것 감사드립니다.

꾸벅~!
   글새미   07-04-09 11:25  
각각의 장점과 원칙을 알고 또한 그것을 사용할 줄 안다면 되는 것 같습니다.
문제는 각 상황에 맞게 짜는 게 더 났지 않나 싶습니다.
 사실 XML파싱하고 DOM으로 생성하는 것을 W3G에서 권장하고 있습니다만
Gleb Lebedev 라는 사람이 createElement 와 innerHTML 성능 테스트를 한 결과 처럼
innerHTML이 속도면에서는 훨씬 더 빠릅니다.(참조:http://ajaxian.com/archives/benchmark-dom-vs-innerhtml)
또한 사용하기도 편하죠. 하지만 과도한 문자열 삽입 등의 퍼포먼스 저하가 우려되는 문제가 있기도 하죠.

 제 개인적인 생각은 익숙한 것도 좋지만, 각 상황에 맞게 개발되고, 짜여져야 한다고 생각합니다.
익숙한 것에만 머물러 있지 않고, 상황에 따라 능동적으로 대처하기 위해 다양한 도구를 알고 다루며, 그것에
대해 심도있게 고민하고, 자기껏으로 소화해야하지 않나 싶습니다.
 JSON을 쓰는 게 편하기는 하지만, 그것을 사용하기 이전에 XML과 DOM에 대해 숙지하고, 알고나서
사용하는 게, 더 났지 않을까요?
   신나군   07-04-09 15:42  
저는 text로만 처리 합니다.

성공적으로 처리되었을경우
_ok|간단한 값

성공하고 html을 뿌려야 할경우
ob_start();
$data = ob_get_contents();
ob_end_clean();
print $data;

처리에 실패했을경우
_error|에러코드

페이지 전체가 ajax로 꾸며져 있진 않아서..이렇게 처리해도 큰 문제는 없던데요~
코멘트 같은 경우는 이렇게 처리하고 있습니다.
너무 무식한 방법인가요? =ㅂ=;;
   칼솜   07-04-09 20:47  
실시간 검색어 같은 경우는 XML로 뽑아와야 좀 편하더군요.
나머지는 html로 뽑아와도 별 무리는 없습니다. (저는요 ㅡㅡ)
행복한 고니님께서 핵심적인 부분에 댓글을 주셔서 도움 많이 되었습니다 ^^


출처 : phpschool
신고
Trackback 1 Comment 0


티스토리 툴바