Geant4 가이드

G4Tool

G4Tool은 histogram을 만들고 저장하거나 Ntuple을 생성하고 여러 파일 포멧으로 저장할 수 있는 분석 툴이다. 이는 Genat4 클래스 G4AnalysisManager로 구현되어 있다. 그렇다면 Ntuple이 무엇인지 그리고 G4AnalysisManager를 통하여 어떻게 사용되는지 알아보자.

NTuple

Ntuple은 간단히 말해서 정렬된 원소의 리스트이다. 가령 우리가 보고자 하는 스텝의 정보 중 eventID, volumeID, energy deposit을 저장하고 싶다고 하자. 이 경우에 NTuple은 (eventID, volumeID, energy deposit)의 리스트가 될 것이다. 이때 하나의 (eventID, volumeID, energy deposit) 세트는 엔트리라고 부른다. 예를 들어서 데이터가 들어가면 다음과 같은 형태를 가진다.

0 0 0.02
0 1 4.89
0 1 4.54
1 0 0.01
1 1 3.78

CSV는 Comma Saparated Values의 약자로 데이터를 저장하는 하나의 형식이다. 한 줄이 하나의 데이터 세트를 이루며 각 원소는 쉼표(,)로 구분한다. 따라서 위 Ntuple을 CSV 형식으로 저장한다면 다음과 같다.

0,0,0.02
0,1,4,89
0,1,4.54
1,0,0.01
1,1,3.78

G4AnalysisManager

Geant4는 G4AnalysisManager로 부터 Ntuple을 생성하고 저장할 수 있다. G4AnalaysisManager의 이점은 코드를 완성한 시점에서 헤더 파일만 변경하면 데이터 저장 형식을 자유롭게 바꿀 수 있다는데에 있다. CSV의 경우 "g4csv.hh", XML의 경우 "g4xml.hh", 그리고 ROOT 파일의 경우 "g4root.hh"를 사용한다.

#include "g4root.hh"

G4Analysismanager의 Ntuple 생성과 저장은 런을 통틀어 한번만 실행하므로 Run Action 에 추가한다. 

G4AnalysisManager 생성
G4AnalysisManager* analysisManager = G4AnalysisManager::Instance();
analysisManager -> OpenFile("data");

OpenFile(이름) 함수에 들어가는 이름은 확장자를 제외한 파일의 이름이다.

G4AnalysmsManager 저장
G4AnalysisManager* analysisManager = G4AnalysisManager::Instance();
analysisManager -> Write();
analysisManager -> CloseFile();

위 코드는 G4AnalysisManager에서 만들어진 모든 데이터를 저장하고 파일을 닫는다.

NTuple 생성
G4AnalysisManager* analysisManager = G4AnalysisManager::Instance();
analysisManager -> CreateNtuple("step", "step");
analysisManager -> CreateNtupleIColumn("eventID");
analysisManager -> CreateNtupleIColumn("volumeID");
analysisManager -> CreateNtupleDColumn("edep");
analysisManager -> FinishNtuple();

Ntuple을 CreateNtuple(이름, 타이틀) 함수로 생성하고 데이터 세트의 각 원소를 CreateNtuple[X]Column(이름) 함수로 생성한다. 여기서 [X]는 알파벳 I(int), F(float), D(double) 중 하나이며 변수의 데이터 타입에 따라 사용자가 설정할 수 있다. eventID와 volumeID는 int 타입으로 충분하므로 I를 사용하고 잃어버린 에너지의 경우 double 타입이기 때문에 D를 사용하였다. 데이터 세트의 각 변수에는 생성된 순서대로 0번 부터 번호가 붙는다. 마지막에 FinishNtuple() 함수를 불러와서 데이터 세트가 완성되었다는 것을 알려주면 Ntuple이 생성된다. Ntuple의 타이틀 그리고 각 변수의 이름은 ROOT 파일로 저장할 경우 저장되지만 CSV 형식에서는 저장되지 않는다.

Ntuple 저장
G4AnalysisManager* analysisManager = G4AnalysisManager::Instance();
analysisManager -> FillNtupleIColumn(0, eventID);
analysisManager -> FillNtupleIColumn(1, volumeID);
analysisManager -> FillNtupleDColumn(2, edep);
analysisManager -> AddNtupleRow();

데이터 값은 FillNtuple[X]Column(변수ID, 값) 함수로 지정한다. 변수ID는 위 Ntuple 생성때 부여된 변수의 번호와 같다. 변수의 값  AddNtupleRow() 함수를 불러와서 Ntuple의 한줄을 확정짓는다. 엔트리를 채울 때는 매 step 마다 저장하므로 Stepping Action에 추가한다.

두개 이상의 Ntuple 생성과 저장

두번째 ntuple 부터는 첫번째 ntuple 과 구분하기 위해서 Ntuple-id 를 사용한다. 첫번째 Ntuple-id 는 0 이며 이후에 생성되는 순서로 1씩 늘어난다.

두번째 Ntuple 생성 (id=1)

FinishNtuple()에 Ntuple-id 를 넣어준다.

//...
analysisManager -> FinishNtuple();

analysisManager -> CreateNtuple("primary", "primary");
analysisManager -> CreateNtupleIColumn("mag");
analysisManager -> CreateNtupleIColumn("theta");
analysisManager -> CreateNtupleIColumn("phi");
analysisManager -> FinishNtuple(1);
두번째 Ntuple 저장 (id=1)

모든 함수의 첫번째 변수로 id=1을 추가로 넣어준다.

analysisManager -> FillNtupleIColumn(1, 0, mag);
analysisManager -> FillNtupleIColumn(1, 1, theta);
analysisManager -> FillNtupleDColumn(1, 2, phi);
analysisManager -> AddNtupleRow(1);

댓글

댓글 본문
  1. 행인1
    안녕하세요 기초적인 질문이 있습니다
    이 코드의 OTEventAection.hh 에서
    void AddEnergyDeposit1(G4double edep) { edep1 += edep; }
    라는 코드에서 Edep1은 정의가 되어있지만
    edep는 정의가 되어있지 않은데 어떻게 계산이 되는것인가요?
    어떤 class를 열어봐도 edep는 ntuple만들때만 사용되는것 같은데 잘모르겠습니다.
    대화보기
    • 행인1
      안녕하세요
      step -> GetNonionizingEnergyDeposit()이라는 함수는 흔히 핵물리학에서 말하는 NIEL값을 말하는건가요?
      만약 위의 내용이 맞다면, 중성자의 NIEL 값은 단순한 충돌에 의해 발생한 stopping power에 대한 energy값이라고 볼 수 있을까요?
    • ejungwoo
      Geant4 에서 나오는 output 파일을 보는 방법은 어떤 분석 프로그램을 사용하든지 가능합니다.

      예를 들어서 root파일은 ROOT라는 c++ 패키지를 이용하여 읽을 수 있습니다. ROOT는 핵물리 분야에서 많이 사용하는 통계 분석 프로그램이며 Geant4와 연관이 아주 깊습니다. 이 프로그램에 대해서는 기초적인 가이드를 제가 만들어 두었습니다(https://opentutorials.org......860).

      ROOT가 아니더라도 csv 파일을 사용하면 최근에 일반적으로 많이 사용하는 python 이나 R 혹은 다른 기타 분석 프로그램으로 파일을 읽어보고 분석할 수 있습니다. 다만 어떤 프로그램을 사용하더라도 해당 프로그램에 대한 공부는 어느정도 필요합니다. 가장 좋은 방법은 사용자의 주변이나 분야에서 가장 많이 사용하는 프로그램을 이용하는 것입니다.
      대화보기
      • 행인1
        안녕하세요 Ntuple을 이용해서 혹은 다른방법을 이용해서 이시스템의 output을 보는 방법이 있을까요?
        계산을 돌리고 나서 나오는 모든 output을 일괄적으로 보고 싶으면 어떤방식으로 해야 할까요?
        그러한 방법이 있을까요?
      • ejungwoo
        csv로 파일 포멧을 바꾼후에 코드 그대로 돌렸을 때 data_nt_edep.csv 라는 파일에 edep1 정보가 저장되어야 합니다. 이 경우가 아니라면 구체적으로 어떤 문제인지 알려주셔야 합니다. 알려주신 정보만으로는 제가 도와드릴 수가 없네요. edep1이 초기화되지 않았다는 메세지는 컴파일시 나오는 메세지 인가요? 그렇다면 이 경우에는 무시하셔도 괜찮습니다.
        대화보기
        • 이핑크
          아래 알려주신대로 했는데요 EventAction.cc 에서

          EventAction::EventAction():
          G4UserEventAction(); {}

          여기서 Member 'edep1'이 이 구조체에서 초기화가 되지 않았다고 뜹니다.

          저는 csv로 했는데도 잘? 돌아가더라구요. /run/beamOn 두번안해도 되더라구요.
          그런데 결과 csv에서 edep1 결과가 안나오는데 어떻게 해야하나요??
        • 그러네요 두번씩 하니까 나오네요 감사합니다 !!!
        • ejungwoo
          저도 방금 이 문제를 확인했습니다. 사실 제가 csv 형식을 쓰지 않아서 이런 문제가 있는지 몰랐는데 이번에 확인하게 되었네요. 제가 테스트를 해 본 결과 버젼에 따라서 되는 경우도(v4.10.03) 안되는 경우도(v4.10.00, v4.10.02) 있었는데요. 안되는 경우에는 /run/beamOn 을 두번 실행하면 두번째에 나오는 결과가 파일에 쓰이더군요.
          제가 이 문제를 확실하게 해결해 드리지는 못할것 같습니다. 만약 나중에 geant4 데이터를 분석하실 예정이라면 root를 배우시는 편을 추천드립니다.
          대화보기
          • 단순히 정우님이 작성해주신 코드에 모든 헤더파일에서 g4root.hh를 인클루드 한걸 g4csv.hh로 바꾸었습니다.
            정우님이 작성하신 코드 기준으로 OTEventAction.hh , OTRunAction.hh, OTSteppingAction.hh 의 헤더파일을 바꿧습니다. 그리고 에러가 발생하는건 아니고 계산을 해도 output파일이 생성되지가 않네요!!

            아래가 계산시 나오는 메세지입니다
            -------- WWWW ------- G4Exception-START -------- WWWW -------
            *** G4Exception : Analysis_W011
            issued by : G4TNtupleManager::AddNtupleRow
            ntupleId 1 does not exist.
            *** This is just a warning message. ***
            -------- WWWW -------- G4Exception-END --------- WWWW -------
          • ejungwoo
            root 파일은 root라는 프로그램을 사용하여 읽어야 합니다. ROOT 가이드(https://opentutorials.org......860) 를 참고하세요. 배우는데 조금 시간을 들여아 합니다.
            코드가 동작하지 않는다면 어떻게 동작하지 않는지, 에러 메세지가 있다면 에러메세지나 작성하신 코드를 보여주셔야 도와드릴 수 있을 것 같습니다.
            대화보기
            • 감사합니다!
              1) g4root 파일로 나오는 data.root 파일은 어떻게 읽을수 있나요?? vi 로 읽으니까 글씨가 다깨져서 나오네요..
              2) 정우님께서 아래 댓글에 작성해주신 코드에서 g4root.hh를 g4csv.hh로 일괄적으로 수정하였더니 코드가
              동작하지 않는군요 헤더파일말고 다른부분을 더바꿔줄곳이 있나요

              p.s 이번에 막 geant4를 시작한 입문자인데 정우님덕분에 큰도움이 되고 있습니다.

              항상 감사합니다 !! 답변도 너무 감사드립니다
            • ejungwoo
              네 맞습니다. g4root.hh 헤더를 사용하면 root 파일로 내보내 줍니다.
              대화보기
              • 안녕하세요 혹시 아래 예제 파일로 적성해주신 코드는 output을 root파일로 내보내 주나요?
              • Kain Kim
                자세히 설명해주셔서 감사합니다!
                대화보기
                • ejungwoo
                  안녕하세요.
                  매 이벤트마다 특정 볼륨안에 누적된 energy loss를 저장하려고 하는것이 맞나요?

                  개인적으로는 Geant4 시뮬레이션에서 나온 데이터 파일을 다시 분석하는 방법이 더 쉽고 빠르다고 생각합니다. 하지만 Geant4 안에서 해결해야 할 상황이라면 다음 링크를 참고하세요.

                  https://github.com......cac

                  위 프로그램은 second_program에서 조금의 변화를 준 케이스 입니다. 간단하게 설명을 하면
                  1) 우리가 보고싶은 볼륨의 volumeID가 '1'이라고 합시다.
                  2) Run Action 클래스에서 edep 이라는 새로운 ntuple을 만들고 edep1 column을 생성합니다.
                  3) 이후 Event Action 클래스를 만들고 한 이벤트 동안 누적된 energy loss를 저장할 edep1이라는 변수를 만들고 Stepping Action에서 더해줄 수 있도록 AddEnergyLoss1 이라는 함수를 만들어 줍니다.
                  4) Stepping Action에서 볼륨1이 확인이 될때마다 AddEnergyLoss1 함수를 이용해서 energy loss를 더해주고
                  5) Event Action에서는 매 이벤트가 끝날 때 마다 edep1을 저장하고 매 이벤트가 시작할 때 마다 edep1의 값을 0으로 초기화니다.

                  만약에 한 개 이상의 볼륨에 대해서 energy loss를 보고 싶다면 edep1과 같은 변수과 함수, 그리고 tuple 안에 새로운 column을 만들어 주면 되겠죠.
                  대화보기
                  버전 관리
                  ejungwoo
                  현재 버전
                  선택 버전
                  graphittie 자세히 보기