tf.summary 사용량을 TF 2.0으로 마이그레이션

TensorFlow.org에서보기 Google Colab에서 실행 GitHub에서 소스보기 노트북 다운로드
import tensorflow as tf

TensorFlow 2.0에는 tf.summary 에서 시각화를위한 요약 데이터를 작성하는 데 사용되는 tf.summary API에 대한 중요한 변경 사항이 포함되어 있습니다.

변경된 사항

tf.summary API를 두 개의 하위 API로 생각하면 유용합니다.

TF 1.x에서

두 반쪽은 Session.run() 통해 요약 작업 출력을 가져오고 FileWriter.add_summary(output, step) 호출 Session.run() 수동으로 함께 연결해야했습니다. v1.summary.merge_all() 은 그래프 컬렉션을 사용하여 모든 요약 작업 출력을 집계 v1.summary.merge_all() 작업을 더 쉽게 만들었지 만,이 접근 방식은 여전히 ​​열성적인 실행 및 제어 흐름에 적합하지 않아 TF 2.0에 특히 적합하지 않습니다.

TF 2.X에서

두 반쪽은 긴밀하게 통합되어 있으며 이제 개별 tf.summary 작업이 실행되는 즉시 데이터를 기록합니다. 모델 코드에서 API를 사용하는 것은 여전히 ​​익숙해 보일 것입니다.하지만 이제는 그래프 모드 호환을 유지하면서 열성적인 실행에 친숙합니다. API의 두 부분을 모두 통합하면 summary.FileWriter 는 이제 TensorFlow 실행 컨텍스트의 일부이며 tf.summary ops에 의해 직접 액세스되므로 작성자 구성이 달라 보이는 주요 부분입니다.

TF 2.0의 기본값 인 즉시 실행을 사용한 예제 사용 :

writer = tf.summary.create_file_writer("/tmp/mylogs/eager")

with writer.as_default():
  for step in range(100):
    # other model code would go here
    tf.summary.scalar("my_metric", 0.5, step=step)
    writer.flush()
ls /tmp/mylogs/eager
events.out.tfevents.1617793798.kokoro-gcp-ubuntu-prod-2000985207.3796.5.v2

tf.function 그래프 실행을 사용한 예제 사용 :

writer = tf.summary.create_file_writer("/tmp/mylogs/tf_function")

@tf.function
def my_func(step):
  with writer.as_default():
    # other model code would go here
    tf.summary.scalar("my_metric", 0.5, step=step)

for step in tf.range(100, dtype=tf.int64):
  my_func(step)
  writer.flush()
ls /tmp/mylogs/tf_function
events.out.tfevents.1617793799.kokoro-gcp-ubuntu-prod-2000985207.3796.1013.v2

레거시 TF 1.x 그래프 실행을 사용한 예제 사용 :

g = tf.compat.v1.Graph()
with g.as_default():
  step = tf.Variable(0, dtype=tf.int64)
  step_update = step.assign_add(1)
  writer = tf.summary.create_file_writer("/tmp/mylogs/session")
  with writer.as_default():
    tf.summary.scalar("my_metric", 0.5, step=step)
  all_summary_ops = tf.compat.v1.summary.all_v2_summary_ops()
  writer_flush = writer.flush()


with tf.compat.v1.Session(graph=g) as sess:
  sess.run([writer.init(), step.initializer])

  for i in range(100):
    sess.run(all_summary_ops)
    sess.run(step_update)
    sess.run(writer_flush)
ls /tmp/mylogs/session
events.out.tfevents.1617793799.kokoro-gcp-ubuntu-prod-2000985207.3796.1446.v2

코드 변환

기존 tf.summary 사용량을 TF 2.0 API로 변환하는 것은 안정적으로 자동화 할 수 없으므로 tf_upgrade_v2 스크립트 는 모든 것을 tf.compat.v1.summary 다시 작성합니다. TF 2.0으로 마이그레이션하려면 다음과 같이 코드를 조정해야합니다.

  1. 요약 작업을 사용하려면 .as_default() 를 통해 설정된 기본 작성기가 있어야합니다.

    • 이는 작업을 열심히 실행하거나 그래프 구성에서 작업을 사용하는 것을 의미합니다.
    • 기본 작성기가 없으면 요약 작업이 무음이됩니다.
    • 기본 작성자는 (아직) @tf.function 실행 경계를 넘어 전파되지 않습니다. 함수가 추적 될 때만 감지됩니다. 따라서 함수 본문 내에서 writer.as_default() 를 호출하고 작성기 객체가 있는지 확인하는 것이 가장 좋습니다. @tf.function 이 사용되는 한 계속 존재합니다.
  2. "step"값은 step 인수를 통해 각 작업에 전달되어야합니다.

    • TensorBoard에서 데이터를 시계열로 렌더링하려면 단계 값이 필요합니다.
    • TF 1.x의 전역 단계가 제거되었으므로 명시 적 전달이 필요하므로 각 작업은 읽을 원하는 단계 변수를 알아야합니다.
    • 상용구를 줄이기 위해 기본 단계 값 등록에 대한 실험적 지원은 tf.summary.experimental.set_step() 으로 제공되지만 이는 예고없이 변경 될 수있는 임시 기능입니다.
  3. 개별 요약 작업의 기능 서명이 변경되었습니다.

    • 반환 값은 이제 부울 (요약이 실제로 작성되었는지 여부를 나타냄)입니다.
    • 두 번째 매개 변수 이름 (사용 된 경우)이 tensor 에서 data 변경되었습니다.
    • collections 매개 변수가 제거되었습니다. 컬렉션은 TF 1.x 전용입니다.
    • family 매개 변수가 제거되었습니다. tf.name_scope() 사용 tf.name_scope()
  4. [레거시 그래프 모드 / 세션 실행 사용자 만 해당]

    • 먼저 v1.Session.run(writer.init()) 작성기를 초기화하십시오.

    • v1.summary.all_v2_summary_ops() 를 사용하여 현재 그래프에 대한 모든 TF 2.0 요약 작업을 가져 v1.summary.all_v2_summary_ops() 예 : Session.run() 통해 실행 Session.run()

    • v1.Session.run(writer.flush()) 작성기를 플러시하고 마찬가지로 close()

TF 1.x 코드가 tf.contrib.summary API를 대신 사용하는 경우 TF 2.0 API와 훨씬 유사하므로 tf_upgrade_v2 스크립트는 대부분의 마이그레이션 단계를 자동화하고 완전히 사용할 수없는 사용에 대해 경고 또는 오류를 내 tf_upgrade_v2 마이그레이션 됨). 대부분의 경우 tf.compat.v2.summary 대한 API 호출을 다시 작성합니다. 당신은 단지 TF와의 호환성을 필요로하는 경우 2.0 이상 당신은 놓을 수 compat.v2 단지로 참조 tf.summary .

추가 팁

위의 중요한 영역 외에도 몇 가지 보조 측면도 변경되었습니다.

  • 조건부 기록 (예 : "100 단계마다 기록")이 새로운 모습으로 변경되었습니다.

    • 작업 및 관련 코드를 제어하려면 일반 if 문 (eager 모드 및 @tf.function 를 통해 @tf.function 에서 작동) 또는 tf.cond
    • 요약 만 제어하려면 새로운 tf.summary.record_if() 컨텍스트 관리자를 사용하고 선택한 부울 조건을 전달합니다.
    • 다음은 TF 1.x 패턴을 대체합니다.

      if condition:
        writer.add_summary()
      
  • tf.compat.v1.Graph 직접 작성하지 않고 대신 추적 기능을 사용합니다.

    • TF 2.0의 그래프 실행은 명시 적 Graph 대신 @tf.function 사용합니다.
    • TF 2.0에서 새로운 추적 스타일 API tf.summary.trace_on()tf.summary.trace_export() 를 사용하여 실행 된 함수 그래프를 기록합니다.
  • tf.summary.FileWriterCache 하여 더 이상 logdir 당 글로벌 라이터 캐싱이 필요 tf.summary.FileWriterCache

    • 사용자는 작성기 개체의 자체 캐싱 / 공유를 구현하거나 별도의 작성기를 사용해야합니다 (후자에 대한 TensorBoard 지원이 진행 중입니다 ).
  • 이벤트 파일 바이너리 표현이 변경되었습니다.

    • TensorBoard 1.x는 이미 새로운 형식을 지원합니다. 이 차이는 이벤트 파일에서 요약 데이터를 수동으로 구문 분석하는 사용자에게만 영향을줍니다.
    • 요약 데이터는 이제 텐서 바이트로 저장됩니다. tf.make_ndarray(event.summary.value[0].tensor) 를 사용하여 numpy로 변환 할 수 있습니다.