그래프 머신으로 표준 플로 100 지수 주식 탐색


본 시리즈[1]의 앞글에서 파이썬 기반의 도형 분석 라이브러리인 NetworkX[2]와Nebula Graph[3]를 이용하여 의 역할 관계를 분석하는 방법을 소개했다.
본고에서 우리는 자바를 바탕으로 하는 도형 분석 라이브러리인 JGraphT[4]와 도형 라이브러리 mxGraph[5]를 어떻게 사용하여 표준 플로 100지수 주식[6] 간의 관련성이 시간에 따라 변화하는 것을 가시화하는지 연구하고자 한다.

데이터 세트 처리


본고에서 사용하는 주요 분석 방법은 [7]와 [8]이다.두 개의 데이터 집합이 있는데 그것이 바로 정점 집합과 사이드 집합이다.

주식 데이터 (정점 집합)


아래의 표준 플로 100지수 주식을 선택하고 각 주식을 하나의 정점으로 모델링한다.각 정점의 속성은 상장회사의 주식 코드와 업계다.
표 1: 예제 교점 세트

인벤토리 관계(에지/관계 세트)



이러한 처리를 통해 우리는 거리의 범위를 [0,2]로 얻었다.이것은 두 주식의 거리가 멀어질수록 수익률 간의 관련성이 낮아진다는 것을 의미한다.
표 2: 에지 세트 예

이런 정점 집합과 변집은 하나의 도형 네트워크를 형성하여 성운 도형 데이터베이스에 저장할 수 있다.

JGraphT


JGraphT는 자바 라이브러리로서 각종 효율적인 유니버설 도형 데이터 구조를 제공할 뿐만 아니라 가장 흔히 볼 수 있는 도형 문제를 해결하기 위해 많은 유용한 알고리즘을 제공한다.JGraphT의 특징은 다음과 같습니다.
  • 방향, 무방향, 가중, 비가중 등 지원
  • 는 단순도, 다중도, 위도를 지원한다.
  • 그림 스트리밍을 위한 전용 교체기(DFS, BFS 등)를 제공합니다.
  • 는 경로 검색, 동구 검측, 착색, 공공 조상, 로밍, 연결성, 일치, 순환 검측, 구역, 절단, 흐름과 중심성 등 대량의 상용 도형 알고리즘을 제공했다.
  • GraphViz에서 손쉽게 가져오기/내보내기내보낸 GraphViz 파일은 시각화 도구 Gephi를 사용하여 분석 및 프레젠테이션에 적용할 수 있습니다.
  • JGraphX, mxGraph, GuavaGraphs 생성기 등 도구와 함께 사용할 때 편리한 그래픽 네트워크 생성을 지원한다.
  • 이제 한번 해 봅시다.
  • JGraphT에 지향도를 생성합니다.
  • import org.jgrapht.*;
    import org.jgrapht.graph.*;
    import org.jgrapht.nio.*;
    import org.jgrapht.nio.dot.*;
    import org.jgrapht.traverse.*;
    
    import java.io.*;
    import java.net.*;
    import java.util.*;
    
    Graph<URI, DefaultEdge> g = new DefaultDirectedGraph<>(DefaultEdge.class);
    
    URI google = new URI("http://www.google.com");
    URI wikipedia = new URI("http://www.wikipedia.org");
    URI jgrapht = new URI("http://www.jgrapht.org");
    
  • 정점을 추가합니다.
  • g.addVertex(google);
    g.addVertex(wikipedia);
    g.addVertex(jgrapht);
    
  • 모서리를 추가합니다.
  • // Add edges to create a linked structure
    
    g.addEdge(jgrapht, wikipedia);
    g.addEdge(google, jgrapht);
    g.addEdge(google, wikipedia);
    g.addEdge(wikipedia, google);
    

    성운도 데이터베이스


    JGraphT는 일반적으로 로컬 파일을 데이터 소스로 사용합니다.정적 네트워크 연구를 할 때 이것은 매우 좋지만 도형 네트워크가 끊임없이 변화한다. 예를 들어 주식 데이터의 도형 네트워크가 매일 변화한다면 새로운 정적 파일을 생성하고 그것을 불러오고 분석할 때마다 좀 번거롭다.이상적인 상황에서 전체 변경 과정은 데이터베이스에 오래 쓸 수 있고 하위 그림이나 전체 그림은 데이터베이스에서 직접 불러와서 분석할 수 있다.본고에서 우리는 네블라 그래프를 도형 데이터를 저장하는 도형 데이터베이스로 사용한다.
    Nebula Graph의 Java 클라이언트 Nebula Java[11]는 Nebula Graph에 액세스하는 두 가지 방법을 제공합니다.하나는 도형 조회 언어 nGQL[12]와 조회 엔진층[13]의 상호작용이다. 이 언어는 보통 하위 그림에 접근하기에 적합하고 복잡한 의미를 지원한다.다른 하나는 API를 통해 하부 저장소 층(저장 프로세스)[14]과 직접 상호작용을 하여 완전한 정점과 변집을 얻는 데 사용한다.네블라자바는 성운도 자체를 방문하는 것 외에도 네오4j[15], 자너스 그래프[16], 스파크[17] 등과 상호작용하는 예시를 제공했다.
    이 문서에서는 API를 사용하여 모든 정점과 모서리를 가져오는 스토리지 계층(스토리지 프로세스)에 직접 액세스합니다.다음 두 인터페이스는 모든 정점과 모서리 데이터를 읽는 데 사용할 수 있습니다.
    // space is the name of the graph space to be scanned, and returnCols is the vertex/edge and its properties to be read.
    // Format of returnCols parameter: {tag1Name: prop1, prop2, tag2Name: prop3, prop4, prop5}
    Iterator<ScanVertexResponse> scanVertex(
                Stringspace, Map<String, List<String>>returnCols);
    Iterator<ScanEdgeResponse> scanEdge(
                Stringspace, Map<String, List<String>>returnCols);
    
  • 클라이언트 및 ScanVertexProcessor를 초기화합니다.ScanVertexProcessor는 읽기 정점 데이터를 디코딩하는 데 사용합니다.
  • MetaClientImpl metaClientImpl = new MetaClientImpl(metaHost, metaPort);
    metaClientImpl.connect();
    StorageClient storageClient = new StorageClientImpl(metaClientImpl);
    Processor processor = new ScanVertexProcessor(metaClientImpl);
    
  • scanVertex 인터페이스를 호출하고 이 인터페이스는 scanVertex Response 대상의 교체기를 되돌려줍니다.
  • Iterator<ScanVertexResponse> iterator =
                    storageClient.scanVertex(spaceName, returnCols);
    
  • 모든 데이터를 읽을 때까지 교체기가 가리키는 scanVertexResponse 대상의 데이터를 계속 읽습니다.읽은 정점 데이터가 저장되어 JGraphT의 그래픽 구조에 추가됩니다.
  • while (iterator.hasNext()) {
      ScanVertexResponse response = iterator.next();
      if (response == null) {
        log.error("Error occurs while scan vertex");
        break;
      }
    
      Result result = processor.process(spaceName, response);
      results.addAll(result.getRows(TAGNAME));
    }
    
    가장자리 데이터를 읽는 것은 상술한 과정과 유사하다.

    JGraphT에서 그래픽 분석

  • JGraphT에 무방향 가중도를 생성합니다.
  • Graph<String, MyEdge> graph = GraphTypeBuilder
                    .undirected()
        .weighted(true)
        .allowingMultipleEdges(true)
        .allowingSelfLoops(false)
        .vertexSupplier(SupplierUtil.createStringSupplier())
        .edgeSupplier(SupplierUtil.createSupplier(MyEdge.class))
        .buildGraph();
    
  • 마지막 단계에서 성운도 공간에서 읽은 정점과 가장자리 데이터를 그림에 추가합니다.
  • for (VertexDomain vertex : vertexDomainList){
        graph.addVertex(vertex.getVid().toString());
        stockIdToName.put(vertex.getVid().toString(), vertex);
    }
    
    for (EdgeDomain edgeDomain : edgeDomainList){
        graph.addEdge(edgeDomain.getSrcid().toString(), edgeDomain.getDstid().toString());
        MyEdge newEdge = graph.getEdge(edgeDomain.getSrcid().toString(), edgeDomain.getDstid().toString());
        graph.setEdgeWeight(newEdge, edgeDomain.getWeight());
    }
    
  • [7]와 [8]에서 언급한 분석 알고리즘과 같이 앞의 그림에 Prim의 최소 생성 트리 알고리즘을 사용하고 봉인된drawGraph 인터페이스를 호출하여 그림을 그린다.
  • Prim 알고리즘은 가중 연결 그림에서 가장 작은 생성 트리를 검색하는 도론의 알고리즘이다.다시 말하면 이 알고리즘이 검색한 변자 집합이 형성한 나무는 그림의 모든 정점을 포함할 뿐만 아니라 모든 변의 최소 권중과 합을 가진다는 것이다.
    SpanningTreeAlgorithm.SpanningTree pMST = new PrimMinimumSpanningTree(graph).getSpanningTree();
    
    Legend.drawGraph(pMST.getEdges(), filename, stockIdToName);
    
  • drawGraph 방법은 도면의 레이아웃과 같은 매개변수 설정을 캡슐화합니다.이런 방법은 같은 부문의 주식을 같은 색깔로 나타내고 비슷한 주식을 한데 묶는다.
  • public class Legend {
    
    ...
    
      public static void drawGraph(Set<MyEdge> edges, String filename, Map<String, VertexDomain> idVertexMap) throws IOException {
         // Creates graph with model
         mxGraph graph = new mxGraph();
         Object parent = graph.getDefaultParent();
    
         // set style
         graph.getModel().beginUpdate();
         mxStylesheet myStylesheet = graph.getStylesheet();
         graph.setStylesheet(setMsStylesheet(myStylesheet));
    
         Map<String, Object> idMap = new HashMap<>();
         Map<String, String> industryColor = new HashMap<>();
    
         int colorIndex = 0;
    
         for (MyEdge edge : edges) {
           Object src, dst;
           if (!idMap.containsKey(edge.getSrc())) {
             VertexDomain srcNode = idVertexMap.get(edge.getSrc());
             String nodeColor;
             if (industryColor.containsKey(srcNode.getIndustry())){
               nodeColor = industryColor.get(srcNode.getIndustry());
             }else {
               nodeColor = COLOR_LIST[colorIndex++];
               industryColor.put(srcNode.getIndustry(), nodeColor);
             }
             src = graph.insertVertex(parent, null, srcNode.getName(), 0, 0, 105, 50, "fillColor=" + nodeColor);
             idMap.put(edge.getSrc(), src);
           } else {
             src = idMap.get(edge.getSrc());
           }
    
           if (!idMap.containsKey(edge.getDst())) {
             VertexDomain dstNode = idVertexMap.get(edge.getDst());
    
             String nodeColor;
             if (industryColor.containsKey(dstNode.getIndustry())){
               nodeColor = industryColor.get(dstNode.getIndustry());
             }else {
               nodeColor = COLOR_LIST[colorIndex++];
               industryColor.put(dstNode.getIndustry(), nodeColor);
             }
    
             dst = graph.insertVertex(parent, null, dstNode.getName(), 0, 0, 105, 50, "fillColor=" + nodeColor);
             idMap.put(edge.getDst(), dst);
           } else {
             dst = idMap.get(edge.getDst());
           }
           graph.insertEdge(parent, null, "", src, dst);
         }
    
         log.info("vertice " + idMap.size());
         log.info("colorsize " + industryColor.size());
    
         mxFastOrganicLayout layout = new mxFastOrganicLayout(graph);
         layout.setMaxIterations(2000);
         //layout.setMinDistanceLimit(10D);
         layout.execute(parent);
    
         graph.getModel().endUpdate();
    
         // Creates an image than can be saved using ImageIO
         BufferedImage image = createBufferedImage(graph, null, 1, Color.WHITE,
                                                   true, null);
    
         // For the sake of this example we display the image in a window
         // Save as JPEG
         File file = new File(filename);
         ImageIO.write(image, "JPEG", file);
    
       }
    
      ...
    
    }
    
  • 시각화된 데이터.
  • 그림1에서 각 정점의 색깔은 그 업계를 대표한다.업무 유사성이 높은 주식이 한자리에 모였지만 관련성이 뚜렷하지 않은 일부 주식도 한자리에 모였기 때문에 그 원인은 따로 연구해야 한다.

    그림1: 2014-01-01년부터 2020-01-01년까지의 주식 데이터에 근거한 분류
  • 다른 시간 창에 기반한 동적 탐색
  • 상술한 결론은 주로 2014-01-01년부터 2020-01-01년까지의 주식 가산을 바탕으로 한다.우리는 또 다른 시도를 했다. 2년 동안 슬라이딩 창과 같은 분석 방법으로 집합조가 시간의 추이에 따라 변화하는지 관찰했다.

    그림2: 2014-01-01년부터 2016-01-01년까지 주식 데이터의 분류

    그림3: 2015-01-01년부터 2017-01-01년까지 주식 데이터의 분류

    그림4: 2016-01-01년부터 2018-01-01년까지 주식 데이터의 분류

    그림5: 2017-01-01년부터 2019-01-01년까지 주식 데이터의 분류

    그림6: 2018-01-01~2020-01-01 주식 데이터에 근거한 분류
    대략적인 분석에 의하면 시간창의 변화에 따라 대다수 업계 내의 주식의 집적성이 상대적으로 좋다고 한다. 이것은 시간의 변화에 따라 같은 업계 내의 각종 주식이 상대적으로 높은 관련성을 유지한다는 것을 의미한다.

    면책 성명


    이 글은 투자 건의로 받아들여져서는 안 된다.거래 정지, 차단기, 거래 제한, 양도, 합병, 주영업무 변경 등 상황으로 인해 본 게시물의 데이터 처리가 정확하지 않을 수 있습니다.우리는 아직 모든 데이터를 하나하나 검사하지 않았다.
    시간의 제한을 받아 본고는 지난 6년 동안 100개의 주식 견본의 데이터만 선정하고 최소 확장 트리의 방법으로만 분류하고 분류했다.미래에 우리는 더 큰 데이터 집합(예를 들어 미국 주식, 파생제품과 디지털 화폐)을 사용하여 더 많은 기계 학습 방법을 시도할 수 있을지도 모른다.
    본고에서 사용한 코드는 [18]를 참조하십시오.

    도구책


    [1]NetworkX, Gephi와 성운도로 권력 게임에서의 관계(제1부분)https://nebula-graph.io/posts/game-of-thrones-relationship-networkx-gephi-nebula-graph/ 분석
    [2] NetworkX, Gephi와 성운도로 권력 게임에서의 관계를 분석한다(제2부분)https://nebula-graph.io/posts/game-of-thrones-relationship-networkx-gephi-nebula-graph-part-two/
    [3] NetworkX: 복잡한 네트워크의 구조, 동력학, 기능을 창설, 조작, 연구하는 데 사용되는 파이톤 소프트웨어 패키지.https://networkx.github.io/
    [4] Nebula Graph: 강력한 분포식, 확장 가능, 번개처럼 빠른 도형 데이터베이스로 C++로 작성되었습니다.https://nebula-graph.io/
    [5] JGraphT: 데이터 구조와 알고리즘을 도론한 자바 라이브러리.https://jgrapht.org/
    [6] mxGraph: 대화형 그래픽과 차트 응용 프로그램을 지원하는 JavaScript 차트 라이브러리입니다.https://jgraph.github.io/mxgraph/
    [7] 보나노, 조바니, 릴로, 파브리지오와 만트니아, 로사리오.(2000). 주식 그룹의 고주파는 서로 관련이 있다.arXiv.조직, 정량 금융 논문.1. 10.1080/713665554.
    [8] Mantegna, R.N. 금융 시장의 등급 구조.유로화피스J.B 11193–197(1999).
    [9] https://graphviz.org/
    [10] https://gephi.org/
    [11] https://github.com/vesoft-inc/nebula-java
    [12] 성운도 조회 언어(nGQL).https://docs.nebula-graph.io/manual-EN/1.overview/1.concepts/2.nGQL-overview/
    [13] 성운도 조회 엔진.https://github.com/vesoft-inc/nebula-graph
    [14] 성운 저장소: 분포식 일치 도형 저장소.https://github.com/vesoft-inc/nebula-storage
    [15] Neo4j.www.neo4j.com
    [16] JanusGraph.janusgraph.org
    [17] Apache Spark.spark.apache.org .
    [18] https://github.com/Judy1992/nebula_scan

    Like what we do ? Star us on GitHub. https://github.com/vesoft-inc/nebula


    애초 2020년 11월 12일https://nebula-graph.io에 발표됐다.

    좋은 웹페이지 즐겨찾기