class_docstr: Model specification given adjacency matrix and labeling.
docstr: Initialize the module spec.
  
  Args:
    matrix: ndarray or nested list with shape [V, V] for the adjacency matrix.
    ops: V-length list of labels for the base ops used. The first and last
      elements are ignored because they are the input and output vertices
      which have no operations. The elements are retained to keep consistent
      indexing.
    data_format: channels_last or channels_first.
  
  Raises:
    ValueError: invalid matrix or ops
docstr_tok: ["Initialize","the","module","spec",".","Args",":","matrix",":","ndarray","or","nested","list","with","shape","[","V",",","V","]","for","the","adjacency","matrix",".","ops",":","V-length","list","of","labels","for","the","base","ops","used",".","The","first","and","last","elements","are","ignored","because","they","are","the","input","and","output","vertices","which","have","no","operations",".","The","elements","are","retained","to","keep","consistent","indexing",".","data_format",":","channels_last","or","channels_first",".","Raises",":","ValueError",":","invalid","matrix","or","ops"]
code: def __init__(self, matrix, ops, data_format="channels_last"):
      """Initialize the module spec.
  
      Args:
        matrix: ndarray or nested list with shape [V, V] for the adjacency matrix.
        ops: V-length list of labels for the base ops used. The first and last
          elements are ignored because they are the input and output vertices
          which have no operations. The elements are retained to keep consistent
          indexing.
        data_format: channels_last or channels_first.
  
      Raises:
        ValueError: invalid matrix or ops
      """
      if not isinstance(matrix, np.ndarray):
          matrix = np.array(matrix)
      shape = np.shape(matrix)
      if len(shape) != 2 or shape[0] != shape[1]:
          raise ValueError("matrix must be square")
      if shape[0] != len(ops):
          raise ValueError("length of ops must match matrix dimensions")
      if not is_upper_triangular(matrix):
          raise ValueError("matrix must be upper triangular")
  
      # Both the original and pruned matrices are deep copies of the matrix and
      # ops so any changes to those after initialization are not recognized by the
      # spec.
      self.original_matrix = copy.deepcopy(matrix)
      self.original_ops = copy.deepcopy(ops)
  
      self.matrix = copy.deepcopy(matrix)
      self.ops = copy.deepcopy(ops)
      self.valid_spec = True
      self._prune()
  
      self.data_format = data_format
  
imports: from __future__ import absolute_import
  from __future__ import division
  from __future__ import print_function
  import copy
  import random
  import time
  import shelve
  import hashlib
  import _pickle
  import numpy
label_desc: Use image node_id 1 to create a new ModelSpec object from inherited base classes: object with example: obj = ModelSpec(matrix, ops, data_format)