/**
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements.  See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership.  The ASF licenses this file
 * to you under the Apache License, Version 2.0 (the
 * "License"); you may not use this file except in compliance
 * with the License.  You may obtain a copy of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
/**
 * Autogenerated by Thrift Compiler (0.13.0)
 *
 * DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
 *  @generated
 */
package org.apache.storm.generated;

@SuppressWarnings({"cast", "rawtypes", "serial", "unchecked", "unused"})
@javax.annotation.Generated(value = "Autogenerated by Thrift Compiler (0.13.0)")
public class OwnerResourceSummary implements org.apache.storm.thrift.TBase<OwnerResourceSummary, OwnerResourceSummary._Fields>, java.io.Serializable, Cloneable, Comparable<OwnerResourceSummary> {
  private static final org.apache.storm.thrift.protocol.TStruct STRUCT_DESC = new org.apache.storm.thrift.protocol.TStruct("OwnerResourceSummary");

  private static final org.apache.storm.thrift.protocol.TField OWNER_FIELD_DESC = new org.apache.storm.thrift.protocol.TField("owner", org.apache.storm.thrift.protocol.TType.STRING, (short)1);
  private static final org.apache.storm.thrift.protocol.TField TOTAL_TOPOLOGIES_FIELD_DESC = new org.apache.storm.thrift.protocol.TField("total_topologies", org.apache.storm.thrift.protocol.TType.I32, (short)2);
  private static final org.apache.storm.thrift.protocol.TField TOTAL_EXECUTORS_FIELD_DESC = new org.apache.storm.thrift.protocol.TField("total_executors", org.apache.storm.thrift.protocol.TType.I32, (short)3);
  private static final org.apache.storm.thrift.protocol.TField TOTAL_WORKERS_FIELD_DESC = new org.apache.storm.thrift.protocol.TField("total_workers", org.apache.storm.thrift.protocol.TType.I32, (short)4);
  private static final org.apache.storm.thrift.protocol.TField MEMORY_USAGE_FIELD_DESC = new org.apache.storm.thrift.protocol.TField("memory_usage", org.apache.storm.thrift.protocol.TType.DOUBLE, (short)5);
  private static final org.apache.storm.thrift.protocol.TField CPU_USAGE_FIELD_DESC = new org.apache.storm.thrift.protocol.TField("cpu_usage", org.apache.storm.thrift.protocol.TType.DOUBLE, (short)6);
  private static final org.apache.storm.thrift.protocol.TField MEMORY_GUARANTEE_FIELD_DESC = new org.apache.storm.thrift.protocol.TField("memory_guarantee", org.apache.storm.thrift.protocol.TType.DOUBLE, (short)7);
  private static final org.apache.storm.thrift.protocol.TField CPU_GUARANTEE_FIELD_DESC = new org.apache.storm.thrift.protocol.TField("cpu_guarantee", org.apache.storm.thrift.protocol.TType.DOUBLE, (short)8);
  private static final org.apache.storm.thrift.protocol.TField MEMORY_GUARANTEE_REMAINING_FIELD_DESC = new org.apache.storm.thrift.protocol.TField("memory_guarantee_remaining", org.apache.storm.thrift.protocol.TType.DOUBLE, (short)9);
  private static final org.apache.storm.thrift.protocol.TField CPU_GUARANTEE_REMAINING_FIELD_DESC = new org.apache.storm.thrift.protocol.TField("cpu_guarantee_remaining", org.apache.storm.thrift.protocol.TType.DOUBLE, (short)10);
  private static final org.apache.storm.thrift.protocol.TField ISOLATED_NODE_GUARANTEE_FIELD_DESC = new org.apache.storm.thrift.protocol.TField("isolated_node_guarantee", org.apache.storm.thrift.protocol.TType.I32, (short)11);
  private static final org.apache.storm.thrift.protocol.TField TOTAL_TASKS_FIELD_DESC = new org.apache.storm.thrift.protocol.TField("total_tasks", org.apache.storm.thrift.protocol.TType.I32, (short)12);
  private static final org.apache.storm.thrift.protocol.TField REQUESTED_ON_HEAP_MEMORY_FIELD_DESC = new org.apache.storm.thrift.protocol.TField("requested_on_heap_memory", org.apache.storm.thrift.protocol.TType.DOUBLE, (short)13);
  private static final org.apache.storm.thrift.protocol.TField REQUESTED_OFF_HEAP_MEMORY_FIELD_DESC = new org.apache.storm.thrift.protocol.TField("requested_off_heap_memory", org.apache.storm.thrift.protocol.TType.DOUBLE, (short)14);
  private static final org.apache.storm.thrift.protocol.TField REQUESTED_TOTAL_MEMORY_FIELD_DESC = new org.apache.storm.thrift.protocol.TField("requested_total_memory", org.apache.storm.thrift.protocol.TType.DOUBLE, (short)15);
  private static final org.apache.storm.thrift.protocol.TField REQUESTED_CPU_FIELD_DESC = new org.apache.storm.thrift.protocol.TField("requested_cpu", org.apache.storm.thrift.protocol.TType.DOUBLE, (short)16);
  private static final org.apache.storm.thrift.protocol.TField ASSIGNED_ON_HEAP_MEMORY_FIELD_DESC = new org.apache.storm.thrift.protocol.TField("assigned_on_heap_memory", org.apache.storm.thrift.protocol.TType.DOUBLE, (short)17);
  private static final org.apache.storm.thrift.protocol.TField ASSIGNED_OFF_HEAP_MEMORY_FIELD_DESC = new org.apache.storm.thrift.protocol.TField("assigned_off_heap_memory", org.apache.storm.thrift.protocol.TType.DOUBLE, (short)18);

  private static final org.apache.storm.thrift.scheme.SchemeFactory STANDARD_SCHEME_FACTORY = new OwnerResourceSummaryStandardSchemeFactory();
  private static final org.apache.storm.thrift.scheme.SchemeFactory TUPLE_SCHEME_FACTORY = new OwnerResourceSummaryTupleSchemeFactory();

  private @org.apache.storm.thrift.annotation.Nullable java.lang.String owner; // required
  private int total_topologies; // optional
  private int total_executors; // optional
  private int total_workers; // optional
  private double memory_usage; // optional
  private double cpu_usage; // optional
  private double memory_guarantee; // optional
  private double cpu_guarantee; // optional
  private double memory_guarantee_remaining; // optional
  private double cpu_guarantee_remaining; // optional
  private int isolated_node_guarantee; // optional
  private int total_tasks; // optional
  private double requested_on_heap_memory; // optional
  private double requested_off_heap_memory; // optional
  private double requested_total_memory; // optional
  private double requested_cpu; // optional
  private double assigned_on_heap_memory; // optional
  private double assigned_off_heap_memory; // optional

  /** The set of fields this struct contains, along with convenience methods for finding and manipulating them. */
  public enum _Fields implements org.apache.storm.thrift.TFieldIdEnum {
    OWNER((short)1, "owner"),
    TOTAL_TOPOLOGIES((short)2, "total_topologies"),
    TOTAL_EXECUTORS((short)3, "total_executors"),
    TOTAL_WORKERS((short)4, "total_workers"),
    MEMORY_USAGE((short)5, "memory_usage"),
    CPU_USAGE((short)6, "cpu_usage"),
    MEMORY_GUARANTEE((short)7, "memory_guarantee"),
    CPU_GUARANTEE((short)8, "cpu_guarantee"),
    MEMORY_GUARANTEE_REMAINING((short)9, "memory_guarantee_remaining"),
    CPU_GUARANTEE_REMAINING((short)10, "cpu_guarantee_remaining"),
    ISOLATED_NODE_GUARANTEE((short)11, "isolated_node_guarantee"),
    TOTAL_TASKS((short)12, "total_tasks"),
    REQUESTED_ON_HEAP_MEMORY((short)13, "requested_on_heap_memory"),
    REQUESTED_OFF_HEAP_MEMORY((short)14, "requested_off_heap_memory"),
    REQUESTED_TOTAL_MEMORY((short)15, "requested_total_memory"),
    REQUESTED_CPU((short)16, "requested_cpu"),
    ASSIGNED_ON_HEAP_MEMORY((short)17, "assigned_on_heap_memory"),
    ASSIGNED_OFF_HEAP_MEMORY((short)18, "assigned_off_heap_memory");

    private static final java.util.Map<java.lang.String, _Fields> byName = new java.util.HashMap<java.lang.String, _Fields>();

    static {
      for (_Fields field : java.util.EnumSet.allOf(_Fields.class)) {
        byName.put(field.getFieldName(), field);
      }
    }

    /**
     * Find the _Fields constant that matches fieldId, or null if its not found.
     */
    @org.apache.storm.thrift.annotation.Nullable
    public static _Fields findByThriftId(int fieldId) {
      switch(fieldId) {
        case 1: // OWNER
          return OWNER;
        case 2: // TOTAL_TOPOLOGIES
          return TOTAL_TOPOLOGIES;
        case 3: // TOTAL_EXECUTORS
          return TOTAL_EXECUTORS;
        case 4: // TOTAL_WORKERS
          return TOTAL_WORKERS;
        case 5: // MEMORY_USAGE
          return MEMORY_USAGE;
        case 6: // CPU_USAGE
          return CPU_USAGE;
        case 7: // MEMORY_GUARANTEE
          return MEMORY_GUARANTEE;
        case 8: // CPU_GUARANTEE
          return CPU_GUARANTEE;
        case 9: // MEMORY_GUARANTEE_REMAINING
          return MEMORY_GUARANTEE_REMAINING;
        case 10: // CPU_GUARANTEE_REMAINING
          return CPU_GUARANTEE_REMAINING;
        case 11: // ISOLATED_NODE_GUARANTEE
          return ISOLATED_NODE_GUARANTEE;
        case 12: // TOTAL_TASKS
          return TOTAL_TASKS;
        case 13: // REQUESTED_ON_HEAP_MEMORY
          return REQUESTED_ON_HEAP_MEMORY;
        case 14: // REQUESTED_OFF_HEAP_MEMORY
          return REQUESTED_OFF_HEAP_MEMORY;
        case 15: // REQUESTED_TOTAL_MEMORY
          return REQUESTED_TOTAL_MEMORY;
        case 16: // REQUESTED_CPU
          return REQUESTED_CPU;
        case 17: // ASSIGNED_ON_HEAP_MEMORY
          return ASSIGNED_ON_HEAP_MEMORY;
        case 18: // ASSIGNED_OFF_HEAP_MEMORY
          return ASSIGNED_OFF_HEAP_MEMORY;
        default:
          return null;
      }
    }

    /**
     * Find the _Fields constant that matches fieldId, throwing an exception
     * if it is not found.
     */
    public static _Fields findByThriftIdOrThrow(int fieldId) {
      _Fields fields = findByThriftId(fieldId);
      if (fields == null) throw new java.lang.IllegalArgumentException("Field " + fieldId + " doesn't exist!");
      return fields;
    }

    /**
     * Find the _Fields constant that matches name, or null if its not found.
     */
    @org.apache.storm.thrift.annotation.Nullable
    public static _Fields findByName(java.lang.String name) {
      return byName.get(name);
    }

    private final short _thriftId;
    private final java.lang.String _fieldName;

    _Fields(short thriftId, java.lang.String fieldName) {
      _thriftId = thriftId;
      _fieldName = fieldName;
    }

    public short getThriftFieldId() {
      return _thriftId;
    }

    public java.lang.String getFieldName() {
      return _fieldName;
    }
  }

  // isset id assignments
  private static final int __TOTAL_TOPOLOGIES_ISSET_ID = 0;
  private static final int __TOTAL_EXECUTORS_ISSET_ID = 1;
  private static final int __TOTAL_WORKERS_ISSET_ID = 2;
  private static final int __MEMORY_USAGE_ISSET_ID = 3;
  private static final int __CPU_USAGE_ISSET_ID = 4;
  private static final int __MEMORY_GUARANTEE_ISSET_ID = 5;
  private static final int __CPU_GUARANTEE_ISSET_ID = 6;
  private static final int __MEMORY_GUARANTEE_REMAINING_ISSET_ID = 7;
  private static final int __CPU_GUARANTEE_REMAINING_ISSET_ID = 8;
  private static final int __ISOLATED_NODE_GUARANTEE_ISSET_ID = 9;
  private static final int __TOTAL_TASKS_ISSET_ID = 10;
  private static final int __REQUESTED_ON_HEAP_MEMORY_ISSET_ID = 11;
  private static final int __REQUESTED_OFF_HEAP_MEMORY_ISSET_ID = 12;
  private static final int __REQUESTED_TOTAL_MEMORY_ISSET_ID = 13;
  private static final int __REQUESTED_CPU_ISSET_ID = 14;
  private static final int __ASSIGNED_ON_HEAP_MEMORY_ISSET_ID = 15;
  private static final int __ASSIGNED_OFF_HEAP_MEMORY_ISSET_ID = 16;
  private int __isset_bitfield = 0;
  private static final _Fields optionals[] = {_Fields.TOTAL_TOPOLOGIES,_Fields.TOTAL_EXECUTORS,_Fields.TOTAL_WORKERS,_Fields.MEMORY_USAGE,_Fields.CPU_USAGE,_Fields.MEMORY_GUARANTEE,_Fields.CPU_GUARANTEE,_Fields.MEMORY_GUARANTEE_REMAINING,_Fields.CPU_GUARANTEE_REMAINING,_Fields.ISOLATED_NODE_GUARANTEE,_Fields.TOTAL_TASKS,_Fields.REQUESTED_ON_HEAP_MEMORY,_Fields.REQUESTED_OFF_HEAP_MEMORY,_Fields.REQUESTED_TOTAL_MEMORY,_Fields.REQUESTED_CPU,_Fields.ASSIGNED_ON_HEAP_MEMORY,_Fields.ASSIGNED_OFF_HEAP_MEMORY};
  public static final java.util.Map<_Fields, org.apache.storm.thrift.meta_data.FieldMetaData> metaDataMap;
  static {
    java.util.Map<_Fields, org.apache.storm.thrift.meta_data.FieldMetaData> tmpMap = new java.util.EnumMap<_Fields, org.apache.storm.thrift.meta_data.FieldMetaData>(_Fields.class);
    tmpMap.put(_Fields.OWNER, new org.apache.storm.thrift.meta_data.FieldMetaData("owner", org.apache.storm.thrift.TFieldRequirementType.REQUIRED, 
        new org.apache.storm.thrift.meta_data.FieldValueMetaData(org.apache.storm.thrift.protocol.TType.STRING)));
    tmpMap.put(_Fields.TOTAL_TOPOLOGIES, new org.apache.storm.thrift.meta_data.FieldMetaData("total_topologies", org.apache.storm.thrift.TFieldRequirementType.OPTIONAL, 
        new org.apache.storm.thrift.meta_data.FieldValueMetaData(org.apache.storm.thrift.protocol.TType.I32)));
    tmpMap.put(_Fields.TOTAL_EXECUTORS, new org.apache.storm.thrift.meta_data.FieldMetaData("total_executors", org.apache.storm.thrift.TFieldRequirementType.OPTIONAL, 
        new org.apache.storm.thrift.meta_data.FieldValueMetaData(org.apache.storm.thrift.protocol.TType.I32)));
    tmpMap.put(_Fields.TOTAL_WORKERS, new org.apache.storm.thrift.meta_data.FieldMetaData("total_workers", org.apache.storm.thrift.TFieldRequirementType.OPTIONAL, 
        new org.apache.storm.thrift.meta_data.FieldValueMetaData(org.apache.storm.thrift.protocol.TType.I32)));
    tmpMap.put(_Fields.MEMORY_USAGE, new org.apache.storm.thrift.meta_data.FieldMetaData("memory_usage", org.apache.storm.thrift.TFieldRequirementType.OPTIONAL, 
        new org.apache.storm.thrift.meta_data.FieldValueMetaData(org.apache.storm.thrift.protocol.TType.DOUBLE)));
    tmpMap.put(_Fields.CPU_USAGE, new org.apache.storm.thrift.meta_data.FieldMetaData("cpu_usage", org.apache.storm.thrift.TFieldRequirementType.OPTIONAL, 
        new org.apache.storm.thrift.meta_data.FieldValueMetaData(org.apache.storm.thrift.protocol.TType.DOUBLE)));
    tmpMap.put(_Fields.MEMORY_GUARANTEE, new org.apache.storm.thrift.meta_data.FieldMetaData("memory_guarantee", org.apache.storm.thrift.TFieldRequirementType.OPTIONAL, 
        new org.apache.storm.thrift.meta_data.FieldValueMetaData(org.apache.storm.thrift.protocol.TType.DOUBLE)));
    tmpMap.put(_Fields.CPU_GUARANTEE, new org.apache.storm.thrift.meta_data.FieldMetaData("cpu_guarantee", org.apache.storm.thrift.TFieldRequirementType.OPTIONAL, 
        new org.apache.storm.thrift.meta_data.FieldValueMetaData(org.apache.storm.thrift.protocol.TType.DOUBLE)));
    tmpMap.put(_Fields.MEMORY_GUARANTEE_REMAINING, new org.apache.storm.thrift.meta_data.FieldMetaData("memory_guarantee_remaining", org.apache.storm.thrift.TFieldRequirementType.OPTIONAL, 
        new org.apache.storm.thrift.meta_data.FieldValueMetaData(org.apache.storm.thrift.protocol.TType.DOUBLE)));
    tmpMap.put(_Fields.CPU_GUARANTEE_REMAINING, new org.apache.storm.thrift.meta_data.FieldMetaData("cpu_guarantee_remaining", org.apache.storm.thrift.TFieldRequirementType.OPTIONAL, 
        new org.apache.storm.thrift.meta_data.FieldValueMetaData(org.apache.storm.thrift.protocol.TType.DOUBLE)));
    tmpMap.put(_Fields.ISOLATED_NODE_GUARANTEE, new org.apache.storm.thrift.meta_data.FieldMetaData("isolated_node_guarantee", org.apache.storm.thrift.TFieldRequirementType.OPTIONAL, 
        new org.apache.storm.thrift.meta_data.FieldValueMetaData(org.apache.storm.thrift.protocol.TType.I32)));
    tmpMap.put(_Fields.TOTAL_TASKS, new org.apache.storm.thrift.meta_data.FieldMetaData("total_tasks", org.apache.storm.thrift.TFieldRequirementType.OPTIONAL, 
        new org.apache.storm.thrift.meta_data.FieldValueMetaData(org.apache.storm.thrift.protocol.TType.I32)));
    tmpMap.put(_Fields.REQUESTED_ON_HEAP_MEMORY, new org.apache.storm.thrift.meta_data.FieldMetaData("requested_on_heap_memory", org.apache.storm.thrift.TFieldRequirementType.OPTIONAL, 
        new org.apache.storm.thrift.meta_data.FieldValueMetaData(org.apache.storm.thrift.protocol.TType.DOUBLE)));
    tmpMap.put(_Fields.REQUESTED_OFF_HEAP_MEMORY, new org.apache.storm.thrift.meta_data.FieldMetaData("requested_off_heap_memory", org.apache.storm.thrift.TFieldRequirementType.OPTIONAL, 
        new org.apache.storm.thrift.meta_data.FieldValueMetaData(org.apache.storm.thrift.protocol.TType.DOUBLE)));
    tmpMap.put(_Fields.REQUESTED_TOTAL_MEMORY, new org.apache.storm.thrift.meta_data.FieldMetaData("requested_total_memory", org.apache.storm.thrift.TFieldRequirementType.OPTIONAL, 
        new org.apache.storm.thrift.meta_data.FieldValueMetaData(org.apache.storm.thrift.protocol.TType.DOUBLE)));
    tmpMap.put(_Fields.REQUESTED_CPU, new org.apache.storm.thrift.meta_data.FieldMetaData("requested_cpu", org.apache.storm.thrift.TFieldRequirementType.OPTIONAL, 
        new org.apache.storm.thrift.meta_data.FieldValueMetaData(org.apache.storm.thrift.protocol.TType.DOUBLE)));
    tmpMap.put(_Fields.ASSIGNED_ON_HEAP_MEMORY, new org.apache.storm.thrift.meta_data.FieldMetaData("assigned_on_heap_memory", org.apache.storm.thrift.TFieldRequirementType.OPTIONAL, 
        new org.apache.storm.thrift.meta_data.FieldValueMetaData(org.apache.storm.thrift.protocol.TType.DOUBLE)));
    tmpMap.put(_Fields.ASSIGNED_OFF_HEAP_MEMORY, new org.apache.storm.thrift.meta_data.FieldMetaData("assigned_off_heap_memory", org.apache.storm.thrift.TFieldRequirementType.OPTIONAL, 
        new org.apache.storm.thrift.meta_data.FieldValueMetaData(org.apache.storm.thrift.protocol.TType.DOUBLE)));
    metaDataMap = java.util.Collections.unmodifiableMap(tmpMap);
    org.apache.storm.thrift.meta_data.FieldMetaData.addStructMetaDataMap(OwnerResourceSummary.class, metaDataMap);
  }

  public OwnerResourceSummary() {
  }

  public OwnerResourceSummary(
    java.lang.String owner)
  {
    this();
    this.owner = owner;
  }

  /**
   * Performs a deep copy on <i>other</i>.
   */
  public OwnerResourceSummary(OwnerResourceSummary other) {
    __isset_bitfield = other.__isset_bitfield;
    if (other.is_set_owner()) {
      this.owner = other.owner;
    }
    this.total_topologies = other.total_topologies;
    this.total_executors = other.total_executors;
    this.total_workers = other.total_workers;
    this.memory_usage = other.memory_usage;
    this.cpu_usage = other.cpu_usage;
    this.memory_guarantee = other.memory_guarantee;
    this.cpu_guarantee = other.cpu_guarantee;
    this.memory_guarantee_remaining = other.memory_guarantee_remaining;
    this.cpu_guarantee_remaining = other.cpu_guarantee_remaining;
    this.isolated_node_guarantee = other.isolated_node_guarantee;
    this.total_tasks = other.total_tasks;
    this.requested_on_heap_memory = other.requested_on_heap_memory;
    this.requested_off_heap_memory = other.requested_off_heap_memory;
    this.requested_total_memory = other.requested_total_memory;
    this.requested_cpu = other.requested_cpu;
    this.assigned_on_heap_memory = other.assigned_on_heap_memory;
    this.assigned_off_heap_memory = other.assigned_off_heap_memory;
  }

  public OwnerResourceSummary deepCopy() {
    return new OwnerResourceSummary(this);
  }

  @Override
  public void clear() {
    this.owner = null;
    set_total_topologies_isSet(false);
    this.total_topologies = 0;
    set_total_executors_isSet(false);
    this.total_executors = 0;
    set_total_workers_isSet(false);
    this.total_workers = 0;
    set_memory_usage_isSet(false);
    this.memory_usage = 0.0;
    set_cpu_usage_isSet(false);
    this.cpu_usage = 0.0;
    set_memory_guarantee_isSet(false);
    this.memory_guarantee = 0.0;
    set_cpu_guarantee_isSet(false);
    this.cpu_guarantee = 0.0;
    set_memory_guarantee_remaining_isSet(false);
    this.memory_guarantee_remaining = 0.0;
    set_cpu_guarantee_remaining_isSet(false);
    this.cpu_guarantee_remaining = 0.0;
    set_isolated_node_guarantee_isSet(false);
    this.isolated_node_guarantee = 0;
    set_total_tasks_isSet(false);
    this.total_tasks = 0;
    set_requested_on_heap_memory_isSet(false);
    this.requested_on_heap_memory = 0.0;
    set_requested_off_heap_memory_isSet(false);
    this.requested_off_heap_memory = 0.0;
    set_requested_total_memory_isSet(false);
    this.requested_total_memory = 0.0;
    set_requested_cpu_isSet(false);
    this.requested_cpu = 0.0;
    set_assigned_on_heap_memory_isSet(false);
    this.assigned_on_heap_memory = 0.0;
    set_assigned_off_heap_memory_isSet(false);
    this.assigned_off_heap_memory = 0.0;
  }

  @org.apache.storm.thrift.annotation.Nullable
  public java.lang.String get_owner() {
    return this.owner;
  }

  public void set_owner(@org.apache.storm.thrift.annotation.Nullable java.lang.String owner) {
    this.owner = owner;
  }

  public void unset_owner() {
    this.owner = null;
  }

  /** Returns true if field owner is set (has been assigned a value) and false otherwise */
  public boolean is_set_owner() {
    return this.owner != null;
  }

  public void set_owner_isSet(boolean value) {
    if (!value) {
      this.owner = null;
    }
  }

  public int get_total_topologies() {
    return this.total_topologies;
  }

  public void set_total_topologies(int total_topologies) {
    this.total_topologies = total_topologies;
    set_total_topologies_isSet(true);
  }

  public void unset_total_topologies() {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.clearBit(__isset_bitfield, __TOTAL_TOPOLOGIES_ISSET_ID);
  }

  /** Returns true if field total_topologies is set (has been assigned a value) and false otherwise */
  public boolean is_set_total_topologies() {
    return org.apache.storm.thrift.EncodingUtils.testBit(__isset_bitfield, __TOTAL_TOPOLOGIES_ISSET_ID);
  }

  public void set_total_topologies_isSet(boolean value) {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.setBit(__isset_bitfield, __TOTAL_TOPOLOGIES_ISSET_ID, value);
  }

  public int get_total_executors() {
    return this.total_executors;
  }

  public void set_total_executors(int total_executors) {
    this.total_executors = total_executors;
    set_total_executors_isSet(true);
  }

  public void unset_total_executors() {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.clearBit(__isset_bitfield, __TOTAL_EXECUTORS_ISSET_ID);
  }

  /** Returns true if field total_executors is set (has been assigned a value) and false otherwise */
  public boolean is_set_total_executors() {
    return org.apache.storm.thrift.EncodingUtils.testBit(__isset_bitfield, __TOTAL_EXECUTORS_ISSET_ID);
  }

  public void set_total_executors_isSet(boolean value) {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.setBit(__isset_bitfield, __TOTAL_EXECUTORS_ISSET_ID, value);
  }

  public int get_total_workers() {
    return this.total_workers;
  }

  public void set_total_workers(int total_workers) {
    this.total_workers = total_workers;
    set_total_workers_isSet(true);
  }

  public void unset_total_workers() {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.clearBit(__isset_bitfield, __TOTAL_WORKERS_ISSET_ID);
  }

  /** Returns true if field total_workers is set (has been assigned a value) and false otherwise */
  public boolean is_set_total_workers() {
    return org.apache.storm.thrift.EncodingUtils.testBit(__isset_bitfield, __TOTAL_WORKERS_ISSET_ID);
  }

  public void set_total_workers_isSet(boolean value) {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.setBit(__isset_bitfield, __TOTAL_WORKERS_ISSET_ID, value);
  }

  public double get_memory_usage() {
    return this.memory_usage;
  }

  public void set_memory_usage(double memory_usage) {
    this.memory_usage = memory_usage;
    set_memory_usage_isSet(true);
  }

  public void unset_memory_usage() {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.clearBit(__isset_bitfield, __MEMORY_USAGE_ISSET_ID);
  }

  /** Returns true if field memory_usage is set (has been assigned a value) and false otherwise */
  public boolean is_set_memory_usage() {
    return org.apache.storm.thrift.EncodingUtils.testBit(__isset_bitfield, __MEMORY_USAGE_ISSET_ID);
  }

  public void set_memory_usage_isSet(boolean value) {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.setBit(__isset_bitfield, __MEMORY_USAGE_ISSET_ID, value);
  }

  public double get_cpu_usage() {
    return this.cpu_usage;
  }

  public void set_cpu_usage(double cpu_usage) {
    this.cpu_usage = cpu_usage;
    set_cpu_usage_isSet(true);
  }

  public void unset_cpu_usage() {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.clearBit(__isset_bitfield, __CPU_USAGE_ISSET_ID);
  }

  /** Returns true if field cpu_usage is set (has been assigned a value) and false otherwise */
  public boolean is_set_cpu_usage() {
    return org.apache.storm.thrift.EncodingUtils.testBit(__isset_bitfield, __CPU_USAGE_ISSET_ID);
  }

  public void set_cpu_usage_isSet(boolean value) {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.setBit(__isset_bitfield, __CPU_USAGE_ISSET_ID, value);
  }

  public double get_memory_guarantee() {
    return this.memory_guarantee;
  }

  public void set_memory_guarantee(double memory_guarantee) {
    this.memory_guarantee = memory_guarantee;
    set_memory_guarantee_isSet(true);
  }

  public void unset_memory_guarantee() {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.clearBit(__isset_bitfield, __MEMORY_GUARANTEE_ISSET_ID);
  }

  /** Returns true if field memory_guarantee is set (has been assigned a value) and false otherwise */
  public boolean is_set_memory_guarantee() {
    return org.apache.storm.thrift.EncodingUtils.testBit(__isset_bitfield, __MEMORY_GUARANTEE_ISSET_ID);
  }

  public void set_memory_guarantee_isSet(boolean value) {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.setBit(__isset_bitfield, __MEMORY_GUARANTEE_ISSET_ID, value);
  }

  public double get_cpu_guarantee() {
    return this.cpu_guarantee;
  }

  public void set_cpu_guarantee(double cpu_guarantee) {
    this.cpu_guarantee = cpu_guarantee;
    set_cpu_guarantee_isSet(true);
  }

  public void unset_cpu_guarantee() {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.clearBit(__isset_bitfield, __CPU_GUARANTEE_ISSET_ID);
  }

  /** Returns true if field cpu_guarantee is set (has been assigned a value) and false otherwise */
  public boolean is_set_cpu_guarantee() {
    return org.apache.storm.thrift.EncodingUtils.testBit(__isset_bitfield, __CPU_GUARANTEE_ISSET_ID);
  }

  public void set_cpu_guarantee_isSet(boolean value) {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.setBit(__isset_bitfield, __CPU_GUARANTEE_ISSET_ID, value);
  }

  public double get_memory_guarantee_remaining() {
    return this.memory_guarantee_remaining;
  }

  public void set_memory_guarantee_remaining(double memory_guarantee_remaining) {
    this.memory_guarantee_remaining = memory_guarantee_remaining;
    set_memory_guarantee_remaining_isSet(true);
  }

  public void unset_memory_guarantee_remaining() {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.clearBit(__isset_bitfield, __MEMORY_GUARANTEE_REMAINING_ISSET_ID);
  }

  /** Returns true if field memory_guarantee_remaining is set (has been assigned a value) and false otherwise */
  public boolean is_set_memory_guarantee_remaining() {
    return org.apache.storm.thrift.EncodingUtils.testBit(__isset_bitfield, __MEMORY_GUARANTEE_REMAINING_ISSET_ID);
  }

  public void set_memory_guarantee_remaining_isSet(boolean value) {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.setBit(__isset_bitfield, __MEMORY_GUARANTEE_REMAINING_ISSET_ID, value);
  }

  public double get_cpu_guarantee_remaining() {
    return this.cpu_guarantee_remaining;
  }

  public void set_cpu_guarantee_remaining(double cpu_guarantee_remaining) {
    this.cpu_guarantee_remaining = cpu_guarantee_remaining;
    set_cpu_guarantee_remaining_isSet(true);
  }

  public void unset_cpu_guarantee_remaining() {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.clearBit(__isset_bitfield, __CPU_GUARANTEE_REMAINING_ISSET_ID);
  }

  /** Returns true if field cpu_guarantee_remaining is set (has been assigned a value) and false otherwise */
  public boolean is_set_cpu_guarantee_remaining() {
    return org.apache.storm.thrift.EncodingUtils.testBit(__isset_bitfield, __CPU_GUARANTEE_REMAINING_ISSET_ID);
  }

  public void set_cpu_guarantee_remaining_isSet(boolean value) {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.setBit(__isset_bitfield, __CPU_GUARANTEE_REMAINING_ISSET_ID, value);
  }

  public int get_isolated_node_guarantee() {
    return this.isolated_node_guarantee;
  }

  public void set_isolated_node_guarantee(int isolated_node_guarantee) {
    this.isolated_node_guarantee = isolated_node_guarantee;
    set_isolated_node_guarantee_isSet(true);
  }

  public void unset_isolated_node_guarantee() {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.clearBit(__isset_bitfield, __ISOLATED_NODE_GUARANTEE_ISSET_ID);
  }

  /** Returns true if field isolated_node_guarantee is set (has been assigned a value) and false otherwise */
  public boolean is_set_isolated_node_guarantee() {
    return org.apache.storm.thrift.EncodingUtils.testBit(__isset_bitfield, __ISOLATED_NODE_GUARANTEE_ISSET_ID);
  }

  public void set_isolated_node_guarantee_isSet(boolean value) {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.setBit(__isset_bitfield, __ISOLATED_NODE_GUARANTEE_ISSET_ID, value);
  }

  public int get_total_tasks() {
    return this.total_tasks;
  }

  public void set_total_tasks(int total_tasks) {
    this.total_tasks = total_tasks;
    set_total_tasks_isSet(true);
  }

  public void unset_total_tasks() {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.clearBit(__isset_bitfield, __TOTAL_TASKS_ISSET_ID);
  }

  /** Returns true if field total_tasks is set (has been assigned a value) and false otherwise */
  public boolean is_set_total_tasks() {
    return org.apache.storm.thrift.EncodingUtils.testBit(__isset_bitfield, __TOTAL_TASKS_ISSET_ID);
  }

  public void set_total_tasks_isSet(boolean value) {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.setBit(__isset_bitfield, __TOTAL_TASKS_ISSET_ID, value);
  }

  public double get_requested_on_heap_memory() {
    return this.requested_on_heap_memory;
  }

  public void set_requested_on_heap_memory(double requested_on_heap_memory) {
    this.requested_on_heap_memory = requested_on_heap_memory;
    set_requested_on_heap_memory_isSet(true);
  }

  public void unset_requested_on_heap_memory() {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.clearBit(__isset_bitfield, __REQUESTED_ON_HEAP_MEMORY_ISSET_ID);
  }

  /** Returns true if field requested_on_heap_memory is set (has been assigned a value) and false otherwise */
  public boolean is_set_requested_on_heap_memory() {
    return org.apache.storm.thrift.EncodingUtils.testBit(__isset_bitfield, __REQUESTED_ON_HEAP_MEMORY_ISSET_ID);
  }

  public void set_requested_on_heap_memory_isSet(boolean value) {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.setBit(__isset_bitfield, __REQUESTED_ON_HEAP_MEMORY_ISSET_ID, value);
  }

  public double get_requested_off_heap_memory() {
    return this.requested_off_heap_memory;
  }

  public void set_requested_off_heap_memory(double requested_off_heap_memory) {
    this.requested_off_heap_memory = requested_off_heap_memory;
    set_requested_off_heap_memory_isSet(true);
  }

  public void unset_requested_off_heap_memory() {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.clearBit(__isset_bitfield, __REQUESTED_OFF_HEAP_MEMORY_ISSET_ID);
  }

  /** Returns true if field requested_off_heap_memory is set (has been assigned a value) and false otherwise */
  public boolean is_set_requested_off_heap_memory() {
    return org.apache.storm.thrift.EncodingUtils.testBit(__isset_bitfield, __REQUESTED_OFF_HEAP_MEMORY_ISSET_ID);
  }

  public void set_requested_off_heap_memory_isSet(boolean value) {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.setBit(__isset_bitfield, __REQUESTED_OFF_HEAP_MEMORY_ISSET_ID, value);
  }

  public double get_requested_total_memory() {
    return this.requested_total_memory;
  }

  public void set_requested_total_memory(double requested_total_memory) {
    this.requested_total_memory = requested_total_memory;
    set_requested_total_memory_isSet(true);
  }

  public void unset_requested_total_memory() {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.clearBit(__isset_bitfield, __REQUESTED_TOTAL_MEMORY_ISSET_ID);
  }

  /** Returns true if field requested_total_memory is set (has been assigned a value) and false otherwise */
  public boolean is_set_requested_total_memory() {
    return org.apache.storm.thrift.EncodingUtils.testBit(__isset_bitfield, __REQUESTED_TOTAL_MEMORY_ISSET_ID);
  }

  public void set_requested_total_memory_isSet(boolean value) {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.setBit(__isset_bitfield, __REQUESTED_TOTAL_MEMORY_ISSET_ID, value);
  }

  public double get_requested_cpu() {
    return this.requested_cpu;
  }

  public void set_requested_cpu(double requested_cpu) {
    this.requested_cpu = requested_cpu;
    set_requested_cpu_isSet(true);
  }

  public void unset_requested_cpu() {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.clearBit(__isset_bitfield, __REQUESTED_CPU_ISSET_ID);
  }

  /** Returns true if field requested_cpu is set (has been assigned a value) and false otherwise */
  public boolean is_set_requested_cpu() {
    return org.apache.storm.thrift.EncodingUtils.testBit(__isset_bitfield, __REQUESTED_CPU_ISSET_ID);
  }

  public void set_requested_cpu_isSet(boolean value) {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.setBit(__isset_bitfield, __REQUESTED_CPU_ISSET_ID, value);
  }

  public double get_assigned_on_heap_memory() {
    return this.assigned_on_heap_memory;
  }

  public void set_assigned_on_heap_memory(double assigned_on_heap_memory) {
    this.assigned_on_heap_memory = assigned_on_heap_memory;
    set_assigned_on_heap_memory_isSet(true);
  }

  public void unset_assigned_on_heap_memory() {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.clearBit(__isset_bitfield, __ASSIGNED_ON_HEAP_MEMORY_ISSET_ID);
  }

  /** Returns true if field assigned_on_heap_memory is set (has been assigned a value) and false otherwise */
  public boolean is_set_assigned_on_heap_memory() {
    return org.apache.storm.thrift.EncodingUtils.testBit(__isset_bitfield, __ASSIGNED_ON_HEAP_MEMORY_ISSET_ID);
  }

  public void set_assigned_on_heap_memory_isSet(boolean value) {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.setBit(__isset_bitfield, __ASSIGNED_ON_HEAP_MEMORY_ISSET_ID, value);
  }

  public double get_assigned_off_heap_memory() {
    return this.assigned_off_heap_memory;
  }

  public void set_assigned_off_heap_memory(double assigned_off_heap_memory) {
    this.assigned_off_heap_memory = assigned_off_heap_memory;
    set_assigned_off_heap_memory_isSet(true);
  }

  public void unset_assigned_off_heap_memory() {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.clearBit(__isset_bitfield, __ASSIGNED_OFF_HEAP_MEMORY_ISSET_ID);
  }

  /** Returns true if field assigned_off_heap_memory is set (has been assigned a value) and false otherwise */
  public boolean is_set_assigned_off_heap_memory() {
    return org.apache.storm.thrift.EncodingUtils.testBit(__isset_bitfield, __ASSIGNED_OFF_HEAP_MEMORY_ISSET_ID);
  }

  public void set_assigned_off_heap_memory_isSet(boolean value) {
    __isset_bitfield = org.apache.storm.thrift.EncodingUtils.setBit(__isset_bitfield, __ASSIGNED_OFF_HEAP_MEMORY_ISSET_ID, value);
  }

  public void setFieldValue(_Fields field, @org.apache.storm.thrift.annotation.Nullable java.lang.Object value) {
    switch (field) {
    case OWNER:
      if (value == null) {
        unset_owner();
      } else {
        set_owner((java.lang.String)value);
      }
      break;

    case TOTAL_TOPOLOGIES:
      if (value == null) {
        unset_total_topologies();
      } else {
        set_total_topologies((java.lang.Integer)value);
      }
      break;

    case TOTAL_EXECUTORS:
      if (value == null) {
        unset_total_executors();
      } else {
        set_total_executors((java.lang.Integer)value);
      }
      break;

    case TOTAL_WORKERS:
      if (value == null) {
        unset_total_workers();
      } else {
        set_total_workers((java.lang.Integer)value);
      }
      break;

    case MEMORY_USAGE:
      if (value == null) {
        unset_memory_usage();
      } else {
        set_memory_usage((java.lang.Double)value);
      }
      break;

    case CPU_USAGE:
      if (value == null) {
        unset_cpu_usage();
      } else {
        set_cpu_usage((java.lang.Double)value);
      }
      break;

    case MEMORY_GUARANTEE:
      if (value == null) {
        unset_memory_guarantee();
      } else {
        set_memory_guarantee((java.lang.Double)value);
      }
      break;

    case CPU_GUARANTEE:
      if (value == null) {
        unset_cpu_guarantee();
      } else {
        set_cpu_guarantee((java.lang.Double)value);
      }
      break;

    case MEMORY_GUARANTEE_REMAINING:
      if (value == null) {
        unset_memory_guarantee_remaining();
      } else {
        set_memory_guarantee_remaining((java.lang.Double)value);
      }
      break;

    case CPU_GUARANTEE_REMAINING:
      if (value == null) {
        unset_cpu_guarantee_remaining();
      } else {
        set_cpu_guarantee_remaining((java.lang.Double)value);
      }
      break;

    case ISOLATED_NODE_GUARANTEE:
      if (value == null) {
        unset_isolated_node_guarantee();
      } else {
        set_isolated_node_guarantee((java.lang.Integer)value);
      }
      break;

    case TOTAL_TASKS:
      if (value == null) {
        unset_total_tasks();
      } else {
        set_total_tasks((java.lang.Integer)value);
      }
      break;

    case REQUESTED_ON_HEAP_MEMORY:
      if (value == null) {
        unset_requested_on_heap_memory();
      } else {
        set_requested_on_heap_memory((java.lang.Double)value);
      }
      break;

    case REQUESTED_OFF_HEAP_MEMORY:
      if (value == null) {
        unset_requested_off_heap_memory();
      } else {
        set_requested_off_heap_memory((java.lang.Double)value);
      }
      break;

    case REQUESTED_TOTAL_MEMORY:
      if (value == null) {
        unset_requested_total_memory();
      } else {
        set_requested_total_memory((java.lang.Double)value);
      }
      break;

    case REQUESTED_CPU:
      if (value == null) {
        unset_requested_cpu();
      } else {
        set_requested_cpu((java.lang.Double)value);
      }
      break;

    case ASSIGNED_ON_HEAP_MEMORY:
      if (value == null) {
        unset_assigned_on_heap_memory();
      } else {
        set_assigned_on_heap_memory((java.lang.Double)value);
      }
      break;

    case ASSIGNED_OFF_HEAP_MEMORY:
      if (value == null) {
        unset_assigned_off_heap_memory();
      } else {
        set_assigned_off_heap_memory((java.lang.Double)value);
      }
      break;

    }
  }

  @org.apache.storm.thrift.annotation.Nullable
  public java.lang.Object getFieldValue(_Fields field) {
    switch (field) {
    case OWNER:
      return get_owner();

    case TOTAL_TOPOLOGIES:
      return get_total_topologies();

    case TOTAL_EXECUTORS:
      return get_total_executors();

    case TOTAL_WORKERS:
      return get_total_workers();

    case MEMORY_USAGE:
      return get_memory_usage();

    case CPU_USAGE:
      return get_cpu_usage();

    case MEMORY_GUARANTEE:
      return get_memory_guarantee();

    case CPU_GUARANTEE:
      return get_cpu_guarantee();

    case MEMORY_GUARANTEE_REMAINING:
      return get_memory_guarantee_remaining();

    case CPU_GUARANTEE_REMAINING:
      return get_cpu_guarantee_remaining();

    case ISOLATED_NODE_GUARANTEE:
      return get_isolated_node_guarantee();

    case TOTAL_TASKS:
      return get_total_tasks();

    case REQUESTED_ON_HEAP_MEMORY:
      return get_requested_on_heap_memory();

    case REQUESTED_OFF_HEAP_MEMORY:
      return get_requested_off_heap_memory();

    case REQUESTED_TOTAL_MEMORY:
      return get_requested_total_memory();

    case REQUESTED_CPU:
      return get_requested_cpu();

    case ASSIGNED_ON_HEAP_MEMORY:
      return get_assigned_on_heap_memory();

    case ASSIGNED_OFF_HEAP_MEMORY:
      return get_assigned_off_heap_memory();

    }
    throw new java.lang.IllegalStateException();
  }

  /** Returns true if field corresponding to fieldID is set (has been assigned a value) and false otherwise */
  public boolean isSet(_Fields field) {
    if (field == null) {
      throw new java.lang.IllegalArgumentException();
    }

    switch (field) {
    case OWNER:
      return is_set_owner();
    case TOTAL_TOPOLOGIES:
      return is_set_total_topologies();
    case TOTAL_EXECUTORS:
      return is_set_total_executors();
    case TOTAL_WORKERS:
      return is_set_total_workers();
    case MEMORY_USAGE:
      return is_set_memory_usage();
    case CPU_USAGE:
      return is_set_cpu_usage();
    case MEMORY_GUARANTEE:
      return is_set_memory_guarantee();
    case CPU_GUARANTEE:
      return is_set_cpu_guarantee();
    case MEMORY_GUARANTEE_REMAINING:
      return is_set_memory_guarantee_remaining();
    case CPU_GUARANTEE_REMAINING:
      return is_set_cpu_guarantee_remaining();
    case ISOLATED_NODE_GUARANTEE:
      return is_set_isolated_node_guarantee();
    case TOTAL_TASKS:
      return is_set_total_tasks();
    case REQUESTED_ON_HEAP_MEMORY:
      return is_set_requested_on_heap_memory();
    case REQUESTED_OFF_HEAP_MEMORY:
      return is_set_requested_off_heap_memory();
    case REQUESTED_TOTAL_MEMORY:
      return is_set_requested_total_memory();
    case REQUESTED_CPU:
      return is_set_requested_cpu();
    case ASSIGNED_ON_HEAP_MEMORY:
      return is_set_assigned_on_heap_memory();
    case ASSIGNED_OFF_HEAP_MEMORY:
      return is_set_assigned_off_heap_memory();
    }
    throw new java.lang.IllegalStateException();
  }

  @Override
  public boolean equals(java.lang.Object that) {
    if (that == null)
      return false;
    if (that instanceof OwnerResourceSummary)
      return this.equals((OwnerResourceSummary)that);
    return false;
  }

  public boolean equals(OwnerResourceSummary that) {
    if (that == null)
      return false;
    if (this == that)
      return true;

    boolean this_present_owner = true && this.is_set_owner();
    boolean that_present_owner = true && that.is_set_owner();
    if (this_present_owner || that_present_owner) {
      if (!(this_present_owner && that_present_owner))
        return false;
      if (!this.owner.equals(that.owner))
        return false;
    }

    boolean this_present_total_topologies = true && this.is_set_total_topologies();
    boolean that_present_total_topologies = true && that.is_set_total_topologies();
    if (this_present_total_topologies || that_present_total_topologies) {
      if (!(this_present_total_topologies && that_present_total_topologies))
        return false;
      if (this.total_topologies != that.total_topologies)
        return false;
    }

    boolean this_present_total_executors = true && this.is_set_total_executors();
    boolean that_present_total_executors = true && that.is_set_total_executors();
    if (this_present_total_executors || that_present_total_executors) {
      if (!(this_present_total_executors && that_present_total_executors))
        return false;
      if (this.total_executors != that.total_executors)
        return false;
    }

    boolean this_present_total_workers = true && this.is_set_total_workers();
    boolean that_present_total_workers = true && that.is_set_total_workers();
    if (this_present_total_workers || that_present_total_workers) {
      if (!(this_present_total_workers && that_present_total_workers))
        return false;
      if (this.total_workers != that.total_workers)
        return false;
    }

    boolean this_present_memory_usage = true && this.is_set_memory_usage();
    boolean that_present_memory_usage = true && that.is_set_memory_usage();
    if (this_present_memory_usage || that_present_memory_usage) {
      if (!(this_present_memory_usage && that_present_memory_usage))
        return false;
      if (this.memory_usage != that.memory_usage)
        return false;
    }

    boolean this_present_cpu_usage = true && this.is_set_cpu_usage();
    boolean that_present_cpu_usage = true && that.is_set_cpu_usage();
    if (this_present_cpu_usage || that_present_cpu_usage) {
      if (!(this_present_cpu_usage && that_present_cpu_usage))
        return false;
      if (this.cpu_usage != that.cpu_usage)
        return false;
    }

    boolean this_present_memory_guarantee = true && this.is_set_memory_guarantee();
    boolean that_present_memory_guarantee = true && that.is_set_memory_guarantee();
    if (this_present_memory_guarantee || that_present_memory_guarantee) {
      if (!(this_present_memory_guarantee && that_present_memory_guarantee))
        return false;
      if (this.memory_guarantee != that.memory_guarantee)
        return false;
    }

    boolean this_present_cpu_guarantee = true && this.is_set_cpu_guarantee();
    boolean that_present_cpu_guarantee = true && that.is_set_cpu_guarantee();
    if (this_present_cpu_guarantee || that_present_cpu_guarantee) {
      if (!(this_present_cpu_guarantee && that_present_cpu_guarantee))
        return false;
      if (this.cpu_guarantee != that.cpu_guarantee)
        return false;
    }

    boolean this_present_memory_guarantee_remaining = true && this.is_set_memory_guarantee_remaining();
    boolean that_present_memory_guarantee_remaining = true && that.is_set_memory_guarantee_remaining();
    if (this_present_memory_guarantee_remaining || that_present_memory_guarantee_remaining) {
      if (!(this_present_memory_guarantee_remaining && that_present_memory_guarantee_remaining))
        return false;
      if (this.memory_guarantee_remaining != that.memory_guarantee_remaining)
        return false;
    }

    boolean this_present_cpu_guarantee_remaining = true && this.is_set_cpu_guarantee_remaining();
    boolean that_present_cpu_guarantee_remaining = true && that.is_set_cpu_guarantee_remaining();
    if (this_present_cpu_guarantee_remaining || that_present_cpu_guarantee_remaining) {
      if (!(this_present_cpu_guarantee_remaining && that_present_cpu_guarantee_remaining))
        return false;
      if (this.cpu_guarantee_remaining != that.cpu_guarantee_remaining)
        return false;
    }

    boolean this_present_isolated_node_guarantee = true && this.is_set_isolated_node_guarantee();
    boolean that_present_isolated_node_guarantee = true && that.is_set_isolated_node_guarantee();
    if (this_present_isolated_node_guarantee || that_present_isolated_node_guarantee) {
      if (!(this_present_isolated_node_guarantee && that_present_isolated_node_guarantee))
        return false;
      if (this.isolated_node_guarantee != that.isolated_node_guarantee)
        return false;
    }

    boolean this_present_total_tasks = true && this.is_set_total_tasks();
    boolean that_present_total_tasks = true && that.is_set_total_tasks();
    if (this_present_total_tasks || that_present_total_tasks) {
      if (!(this_present_total_tasks && that_present_total_tasks))
        return false;
      if (this.total_tasks != that.total_tasks)
        return false;
    }

    boolean this_present_requested_on_heap_memory = true && this.is_set_requested_on_heap_memory();
    boolean that_present_requested_on_heap_memory = true && that.is_set_requested_on_heap_memory();
    if (this_present_requested_on_heap_memory || that_present_requested_on_heap_memory) {
      if (!(this_present_requested_on_heap_memory && that_present_requested_on_heap_memory))
        return false;
      if (this.requested_on_heap_memory != that.requested_on_heap_memory)
        return false;
    }

    boolean this_present_requested_off_heap_memory = true && this.is_set_requested_off_heap_memory();
    boolean that_present_requested_off_heap_memory = true && that.is_set_requested_off_heap_memory();
    if (this_present_requested_off_heap_memory || that_present_requested_off_heap_memory) {
      if (!(this_present_requested_off_heap_memory && that_present_requested_off_heap_memory))
        return false;
      if (this.requested_off_heap_memory != that.requested_off_heap_memory)
        return false;
    }

    boolean this_present_requested_total_memory = true && this.is_set_requested_total_memory();
    boolean that_present_requested_total_memory = true && that.is_set_requested_total_memory();
    if (this_present_requested_total_memory || that_present_requested_total_memory) {
      if (!(this_present_requested_total_memory && that_present_requested_total_memory))
        return false;
      if (this.requested_total_memory != that.requested_total_memory)
        return false;
    }

    boolean this_present_requested_cpu = true && this.is_set_requested_cpu();
    boolean that_present_requested_cpu = true && that.is_set_requested_cpu();
    if (this_present_requested_cpu || that_present_requested_cpu) {
      if (!(this_present_requested_cpu && that_present_requested_cpu))
        return false;
      if (this.requested_cpu != that.requested_cpu)
        return false;
    }

    boolean this_present_assigned_on_heap_memory = true && this.is_set_assigned_on_heap_memory();
    boolean that_present_assigned_on_heap_memory = true && that.is_set_assigned_on_heap_memory();
    if (this_present_assigned_on_heap_memory || that_present_assigned_on_heap_memory) {
      if (!(this_present_assigned_on_heap_memory && that_present_assigned_on_heap_memory))
        return false;
      if (this.assigned_on_heap_memory != that.assigned_on_heap_memory)
        return false;
    }

    boolean this_present_assigned_off_heap_memory = true && this.is_set_assigned_off_heap_memory();
    boolean that_present_assigned_off_heap_memory = true && that.is_set_assigned_off_heap_memory();
    if (this_present_assigned_off_heap_memory || that_present_assigned_off_heap_memory) {
      if (!(this_present_assigned_off_heap_memory && that_present_assigned_off_heap_memory))
        return false;
      if (this.assigned_off_heap_memory != that.assigned_off_heap_memory)
        return false;
    }

    return true;
  }

  @Override
  public int hashCode() {
    int hashCode = 1;

    hashCode = hashCode * 8191 + ((is_set_owner()) ? 131071 : 524287);
    if (is_set_owner())
      hashCode = hashCode * 8191 + owner.hashCode();

    hashCode = hashCode * 8191 + ((is_set_total_topologies()) ? 131071 : 524287);
    if (is_set_total_topologies())
      hashCode = hashCode * 8191 + total_topologies;

    hashCode = hashCode * 8191 + ((is_set_total_executors()) ? 131071 : 524287);
    if (is_set_total_executors())
      hashCode = hashCode * 8191 + total_executors;

    hashCode = hashCode * 8191 + ((is_set_total_workers()) ? 131071 : 524287);
    if (is_set_total_workers())
      hashCode = hashCode * 8191 + total_workers;

    hashCode = hashCode * 8191 + ((is_set_memory_usage()) ? 131071 : 524287);
    if (is_set_memory_usage())
      hashCode = hashCode * 8191 + org.apache.storm.thrift.TBaseHelper.hashCode(memory_usage);

    hashCode = hashCode * 8191 + ((is_set_cpu_usage()) ? 131071 : 524287);
    if (is_set_cpu_usage())
      hashCode = hashCode * 8191 + org.apache.storm.thrift.TBaseHelper.hashCode(cpu_usage);

    hashCode = hashCode * 8191 + ((is_set_memory_guarantee()) ? 131071 : 524287);
    if (is_set_memory_guarantee())
      hashCode = hashCode * 8191 + org.apache.storm.thrift.TBaseHelper.hashCode(memory_guarantee);

    hashCode = hashCode * 8191 + ((is_set_cpu_guarantee()) ? 131071 : 524287);
    if (is_set_cpu_guarantee())
      hashCode = hashCode * 8191 + org.apache.storm.thrift.TBaseHelper.hashCode(cpu_guarantee);

    hashCode = hashCode * 8191 + ((is_set_memory_guarantee_remaining()) ? 131071 : 524287);
    if (is_set_memory_guarantee_remaining())
      hashCode = hashCode * 8191 + org.apache.storm.thrift.TBaseHelper.hashCode(memory_guarantee_remaining);

    hashCode = hashCode * 8191 + ((is_set_cpu_guarantee_remaining()) ? 131071 : 524287);
    if (is_set_cpu_guarantee_remaining())
      hashCode = hashCode * 8191 + org.apache.storm.thrift.TBaseHelper.hashCode(cpu_guarantee_remaining);

    hashCode = hashCode * 8191 + ((is_set_isolated_node_guarantee()) ? 131071 : 524287);
    if (is_set_isolated_node_guarantee())
      hashCode = hashCode * 8191 + isolated_node_guarantee;

    hashCode = hashCode * 8191 + ((is_set_total_tasks()) ? 131071 : 524287);
    if (is_set_total_tasks())
      hashCode = hashCode * 8191 + total_tasks;

    hashCode = hashCode * 8191 + ((is_set_requested_on_heap_memory()) ? 131071 : 524287);
    if (is_set_requested_on_heap_memory())
      hashCode = hashCode * 8191 + org.apache.storm.thrift.TBaseHelper.hashCode(requested_on_heap_memory);

    hashCode = hashCode * 8191 + ((is_set_requested_off_heap_memory()) ? 131071 : 524287);
    if (is_set_requested_off_heap_memory())
      hashCode = hashCode * 8191 + org.apache.storm.thrift.TBaseHelper.hashCode(requested_off_heap_memory);

    hashCode = hashCode * 8191 + ((is_set_requested_total_memory()) ? 131071 : 524287);
    if (is_set_requested_total_memory())
      hashCode = hashCode * 8191 + org.apache.storm.thrift.TBaseHelper.hashCode(requested_total_memory);

    hashCode = hashCode * 8191 + ((is_set_requested_cpu()) ? 131071 : 524287);
    if (is_set_requested_cpu())
      hashCode = hashCode * 8191 + org.apache.storm.thrift.TBaseHelper.hashCode(requested_cpu);

    hashCode = hashCode * 8191 + ((is_set_assigned_on_heap_memory()) ? 131071 : 524287);
    if (is_set_assigned_on_heap_memory())
      hashCode = hashCode * 8191 + org.apache.storm.thrift.TBaseHelper.hashCode(assigned_on_heap_memory);

    hashCode = hashCode * 8191 + ((is_set_assigned_off_heap_memory()) ? 131071 : 524287);
    if (is_set_assigned_off_heap_memory())
      hashCode = hashCode * 8191 + org.apache.storm.thrift.TBaseHelper.hashCode(assigned_off_heap_memory);

    return hashCode;
  }

  @Override
  public int compareTo(OwnerResourceSummary other) {
    if (!getClass().equals(other.getClass())) {
      return getClass().getName().compareTo(other.getClass().getName());
    }

    int lastComparison = 0;

    lastComparison = java.lang.Boolean.valueOf(is_set_owner()).compareTo(other.is_set_owner());
    if (lastComparison != 0) {
      return lastComparison;
    }
    if (is_set_owner()) {
      lastComparison = org.apache.storm.thrift.TBaseHelper.compareTo(this.owner, other.owner);
      if (lastComparison != 0) {
        return lastComparison;
      }
    }
    lastComparison = java.lang.Boolean.valueOf(is_set_total_topologies()).compareTo(other.is_set_total_topologies());
    if (lastComparison != 0) {
      return lastComparison;
    }
    if (is_set_total_topologies()) {
      lastComparison = org.apache.storm.thrift.TBaseHelper.compareTo(this.total_topologies, other.total_topologies);
      if (lastComparison != 0) {
        return lastComparison;
      }
    }
    lastComparison = java.lang.Boolean.valueOf(is_set_total_executors()).compareTo(other.is_set_total_executors());
    if (lastComparison != 0) {
      return lastComparison;
    }
    if (is_set_total_executors()) {
      lastComparison = org.apache.storm.thrift.TBaseHelper.compareTo(this.total_executors, other.total_executors);
      if (lastComparison != 0) {
        return lastComparison;
      }
    }
    lastComparison = java.lang.Boolean.valueOf(is_set_total_workers()).compareTo(other.is_set_total_workers());
    if (lastComparison != 0) {
      return lastComparison;
    }
    if (is_set_total_workers()) {
      lastComparison = org.apache.storm.thrift.TBaseHelper.compareTo(this.total_workers, other.total_workers);
      if (lastComparison != 0) {
        return lastComparison;
      }
    }
    lastComparison = java.lang.Boolean.valueOf(is_set_memory_usage()).compareTo(other.is_set_memory_usage());
    if (lastComparison != 0) {
      return lastComparison;
    }
    if (is_set_memory_usage()) {
      lastComparison = org.apache.storm.thrift.TBaseHelper.compareTo(this.memory_usage, other.memory_usage);
      if (lastComparison != 0) {
        return lastComparison;
      }
    }
    lastComparison = java.lang.Boolean.valueOf(is_set_cpu_usage()).compareTo(other.is_set_cpu_usage());
    if (lastComparison != 0) {
      return lastComparison;
    }
    if (is_set_cpu_usage()) {
      lastComparison = org.apache.storm.thrift.TBaseHelper.compareTo(this.cpu_usage, other.cpu_usage);
      if (lastComparison != 0) {
        return lastComparison;
      }
    }
    lastComparison = java.lang.Boolean.valueOf(is_set_memory_guarantee()).compareTo(other.is_set_memory_guarantee());
    if (lastComparison != 0) {
      return lastComparison;
    }
    if (is_set_memory_guarantee()) {
      lastComparison = org.apache.storm.thrift.TBaseHelper.compareTo(this.memory_guarantee, other.memory_guarantee);
      if (lastComparison != 0) {
        return lastComparison;
      }
    }
    lastComparison = java.lang.Boolean.valueOf(is_set_cpu_guarantee()).compareTo(other.is_set_cpu_guarantee());
    if (lastComparison != 0) {
      return lastComparison;
    }
    if (is_set_cpu_guarantee()) {
      lastComparison = org.apache.storm.thrift.TBaseHelper.compareTo(this.cpu_guarantee, other.cpu_guarantee);
      if (lastComparison != 0) {
        return lastComparison;
      }
    }
    lastComparison = java.lang.Boolean.valueOf(is_set_memory_guarantee_remaining()).compareTo(other.is_set_memory_guarantee_remaining());
    if (lastComparison != 0) {
      return lastComparison;
    }
    if (is_set_memory_guarantee_remaining()) {
      lastComparison = org.apache.storm.thrift.TBaseHelper.compareTo(this.memory_guarantee_remaining, other.memory_guarantee_remaining);
      if (lastComparison != 0) {
        return lastComparison;
      }
    }
    lastComparison = java.lang.Boolean.valueOf(is_set_cpu_guarantee_remaining()).compareTo(other.is_set_cpu_guarantee_remaining());
    if (lastComparison != 0) {
      return lastComparison;
    }
    if (is_set_cpu_guarantee_remaining()) {
      lastComparison = org.apache.storm.thrift.TBaseHelper.compareTo(this.cpu_guarantee_remaining, other.cpu_guarantee_remaining);
      if (lastComparison != 0) {
        return lastComparison;
      }
    }
    lastComparison = java.lang.Boolean.valueOf(is_set_isolated_node_guarantee()).compareTo(other.is_set_isolated_node_guarantee());
    if (lastComparison != 0) {
      return lastComparison;
    }
    if (is_set_isolated_node_guarantee()) {
      lastComparison = org.apache.storm.thrift.TBaseHelper.compareTo(this.isolated_node_guarantee, other.isolated_node_guarantee);
      if (lastComparison != 0) {
        return lastComparison;
      }
    }
    lastComparison = java.lang.Boolean.valueOf(is_set_total_tasks()).compareTo(other.is_set_total_tasks());
    if (lastComparison != 0) {
      return lastComparison;
    }
    if (is_set_total_tasks()) {
      lastComparison = org.apache.storm.thrift.TBaseHelper.compareTo(this.total_tasks, other.total_tasks);
      if (lastComparison != 0) {
        return lastComparison;
      }
    }
    lastComparison = java.lang.Boolean.valueOf(is_set_requested_on_heap_memory()).compareTo(other.is_set_requested_on_heap_memory());
    if (lastComparison != 0) {
      return lastComparison;
    }
    if (is_set_requested_on_heap_memory()) {
      lastComparison = org.apache.storm.thrift.TBaseHelper.compareTo(this.requested_on_heap_memory, other.requested_on_heap_memory);
      if (lastComparison != 0) {
        return lastComparison;
      }
    }
    lastComparison = java.lang.Boolean.valueOf(is_set_requested_off_heap_memory()).compareTo(other.is_set_requested_off_heap_memory());
    if (lastComparison != 0) {
      return lastComparison;
    }
    if (is_set_requested_off_heap_memory()) {
      lastComparison = org.apache.storm.thrift.TBaseHelper.compareTo(this.requested_off_heap_memory, other.requested_off_heap_memory);
      if (lastComparison != 0) {
        return lastComparison;
      }
    }
    lastComparison = java.lang.Boolean.valueOf(is_set_requested_total_memory()).compareTo(other.is_set_requested_total_memory());
    if (lastComparison != 0) {
      return lastComparison;
    }
    if (is_set_requested_total_memory()) {
      lastComparison = org.apache.storm.thrift.TBaseHelper.compareTo(this.requested_total_memory, other.requested_total_memory);
      if (lastComparison != 0) {
        return lastComparison;
      }
    }
    lastComparison = java.lang.Boolean.valueOf(is_set_requested_cpu()).compareTo(other.is_set_requested_cpu());
    if (lastComparison != 0) {
      return lastComparison;
    }
    if (is_set_requested_cpu()) {
      lastComparison = org.apache.storm.thrift.TBaseHelper.compareTo(this.requested_cpu, other.requested_cpu);
      if (lastComparison != 0) {
        return lastComparison;
      }
    }
    lastComparison = java.lang.Boolean.valueOf(is_set_assigned_on_heap_memory()).compareTo(other.is_set_assigned_on_heap_memory());
    if (lastComparison != 0) {
      return lastComparison;
    }
    if (is_set_assigned_on_heap_memory()) {
      lastComparison = org.apache.storm.thrift.TBaseHelper.compareTo(this.assigned_on_heap_memory, other.assigned_on_heap_memory);
      if (lastComparison != 0) {
        return lastComparison;
      }
    }
    lastComparison = java.lang.Boolean.valueOf(is_set_assigned_off_heap_memory()).compareTo(other.is_set_assigned_off_heap_memory());
    if (lastComparison != 0) {
      return lastComparison;
    }
    if (is_set_assigned_off_heap_memory()) {
      lastComparison = org.apache.storm.thrift.TBaseHelper.compareTo(this.assigned_off_heap_memory, other.assigned_off_heap_memory);
      if (lastComparison != 0) {
        return lastComparison;
      }
    }
    return 0;
  }

  @org.apache.storm.thrift.annotation.Nullable
  public _Fields fieldForId(int fieldId) {
    return _Fields.findByThriftId(fieldId);
  }

  public void read(org.apache.storm.thrift.protocol.TProtocol iprot) throws org.apache.storm.thrift.TException {
    scheme(iprot).read(iprot, this);
  }

  public void write(org.apache.storm.thrift.protocol.TProtocol oprot) throws org.apache.storm.thrift.TException {
    scheme(oprot).write(oprot, this);
  }

  @Override
  public java.lang.String toString() {
    java.lang.StringBuilder sb = new java.lang.StringBuilder("OwnerResourceSummary(");
    boolean first = true;

    sb.append("owner:");
    if (this.owner == null) {
      sb.append("null");
    } else {
      sb.append(this.owner);
    }
    first = false;
    if (is_set_total_topologies()) {
      if (!first) sb.append(", ");
      sb.append("total_topologies:");
      sb.append(this.total_topologies);
      first = false;
    }
    if (is_set_total_executors()) {
      if (!first) sb.append(", ");
      sb.append("total_executors:");
      sb.append(this.total_executors);
      first = false;
    }
    if (is_set_total_workers()) {
      if (!first) sb.append(", ");
      sb.append("total_workers:");
      sb.append(this.total_workers);
      first = false;
    }
    if (is_set_memory_usage()) {
      if (!first) sb.append(", ");
      sb.append("memory_usage:");
      sb.append(this.memory_usage);
      first = false;
    }
    if (is_set_cpu_usage()) {
      if (!first) sb.append(", ");
      sb.append("cpu_usage:");
      sb.append(this.cpu_usage);
      first = false;
    }
    if (is_set_memory_guarantee()) {
      if (!first) sb.append(", ");
      sb.append("memory_guarantee:");
      sb.append(this.memory_guarantee);
      first = false;
    }
    if (is_set_cpu_guarantee()) {
      if (!first) sb.append(", ");
      sb.append("cpu_guarantee:");
      sb.append(this.cpu_guarantee);
      first = false;
    }
    if (is_set_memory_guarantee_remaining()) {
      if (!first) sb.append(", ");
      sb.append("memory_guarantee_remaining:");
      sb.append(this.memory_guarantee_remaining);
      first = false;
    }
    if (is_set_cpu_guarantee_remaining()) {
      if (!first) sb.append(", ");
      sb.append("cpu_guarantee_remaining:");
      sb.append(this.cpu_guarantee_remaining);
      first = false;
    }
    if (is_set_isolated_node_guarantee()) {
      if (!first) sb.append(", ");
      sb.append("isolated_node_guarantee:");
      sb.append(this.isolated_node_guarantee);
      first = false;
    }
    if (is_set_total_tasks()) {
      if (!first) sb.append(", ");
      sb.append("total_tasks:");
      sb.append(this.total_tasks);
      first = false;
    }
    if (is_set_requested_on_heap_memory()) {
      if (!first) sb.append(", ");
      sb.append("requested_on_heap_memory:");
      sb.append(this.requested_on_heap_memory);
      first = false;
    }
    if (is_set_requested_off_heap_memory()) {
      if (!first) sb.append(", ");
      sb.append("requested_off_heap_memory:");
      sb.append(this.requested_off_heap_memory);
      first = false;
    }
    if (is_set_requested_total_memory()) {
      if (!first) sb.append(", ");
      sb.append("requested_total_memory:");
      sb.append(this.requested_total_memory);
      first = false;
    }
    if (is_set_requested_cpu()) {
      if (!first) sb.append(", ");
      sb.append("requested_cpu:");
      sb.append(this.requested_cpu);
      first = false;
    }
    if (is_set_assigned_on_heap_memory()) {
      if (!first) sb.append(", ");
      sb.append("assigned_on_heap_memory:");
      sb.append(this.assigned_on_heap_memory);
      first = false;
    }
    if (is_set_assigned_off_heap_memory()) {
      if (!first) sb.append(", ");
      sb.append("assigned_off_heap_memory:");
      sb.append(this.assigned_off_heap_memory);
      first = false;
    }
    sb.append(")");
    return sb.toString();
  }

  public void validate() throws org.apache.storm.thrift.TException {
    // check for required fields
    if (!is_set_owner()) {
      throw new org.apache.storm.thrift.protocol.TProtocolException("Required field 'owner' is unset! Struct:" + toString());
    }

    // check for sub-struct validity
  }

  private void writeObject(java.io.ObjectOutputStream out) throws java.io.IOException {
    try {
      write(new org.apache.storm.thrift.protocol.TCompactProtocol(new org.apache.storm.thrift.transport.TIOStreamTransport(out)));
    } catch (org.apache.storm.thrift.TException te) {
      throw new java.io.IOException(te);
    }
  }

  private void readObject(java.io.ObjectInputStream in) throws java.io.IOException, java.lang.ClassNotFoundException {
    try {
      // it doesn't seem like you should have to do this, but java serialization is wacky, and doesn't call the default constructor.
      __isset_bitfield = 0;
      read(new org.apache.storm.thrift.protocol.TCompactProtocol(new org.apache.storm.thrift.transport.TIOStreamTransport(in)));
    } catch (org.apache.storm.thrift.TException te) {
      throw new java.io.IOException(te);
    }
  }

  private static class OwnerResourceSummaryStandardSchemeFactory implements org.apache.storm.thrift.scheme.SchemeFactory {
    public OwnerResourceSummaryStandardScheme getScheme() {
      return new OwnerResourceSummaryStandardScheme();
    }
  }

  private static class OwnerResourceSummaryStandardScheme extends org.apache.storm.thrift.scheme.StandardScheme<OwnerResourceSummary> {

    public void read(org.apache.storm.thrift.protocol.TProtocol iprot, OwnerResourceSummary struct) throws org.apache.storm.thrift.TException {
      org.apache.storm.thrift.protocol.TField schemeField;
      iprot.readStructBegin();
      while (true)
      {
        schemeField = iprot.readFieldBegin();
        if (schemeField.type == org.apache.storm.thrift.protocol.TType.STOP) { 
          break;
        }
        switch (schemeField.id) {
          case 1: // OWNER
            if (schemeField.type == org.apache.storm.thrift.protocol.TType.STRING) {
              struct.owner = iprot.readString();
              struct.set_owner_isSet(true);
            } else { 
              org.apache.storm.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type);
            }
            break;
          case 2: // TOTAL_TOPOLOGIES
            if (schemeField.type == org.apache.storm.thrift.protocol.TType.I32) {
              struct.total_topologies = iprot.readI32();
              struct.set_total_topologies_isSet(true);
            } else { 
              org.apache.storm.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type);
            }
            break;
          case 3: // TOTAL_EXECUTORS
            if (schemeField.type == org.apache.storm.thrift.protocol.TType.I32) {
              struct.total_executors = iprot.readI32();
              struct.set_total_executors_isSet(true);
            } else { 
              org.apache.storm.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type);
            }
            break;
          case 4: // TOTAL_WORKERS
            if (schemeField.type == org.apache.storm.thrift.protocol.TType.I32) {
              struct.total_workers = iprot.readI32();
              struct.set_total_workers_isSet(true);
            } else { 
              org.apache.storm.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type);
            }
            break;
          case 5: // MEMORY_USAGE
            if (schemeField.type == org.apache.storm.thrift.protocol.TType.DOUBLE) {
              struct.memory_usage = iprot.readDouble();
              struct.set_memory_usage_isSet(true);
            } else { 
              org.apache.storm.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type);
            }
            break;
          case 6: // CPU_USAGE
            if (schemeField.type == org.apache.storm.thrift.protocol.TType.DOUBLE) {
              struct.cpu_usage = iprot.readDouble();
              struct.set_cpu_usage_isSet(true);
            } else { 
              org.apache.storm.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type);
            }
            break;
          case 7: // MEMORY_GUARANTEE
            if (schemeField.type == org.apache.storm.thrift.protocol.TType.DOUBLE) {
              struct.memory_guarantee = iprot.readDouble();
              struct.set_memory_guarantee_isSet(true);
            } else { 
              org.apache.storm.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type);
            }
            break;
          case 8: // CPU_GUARANTEE
            if (schemeField.type == org.apache.storm.thrift.protocol.TType.DOUBLE) {
              struct.cpu_guarantee = iprot.readDouble();
              struct.set_cpu_guarantee_isSet(true);
            } else { 
              org.apache.storm.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type);
            }
            break;
          case 9: // MEMORY_GUARANTEE_REMAINING
            if (schemeField.type == org.apache.storm.thrift.protocol.TType.DOUBLE) {
              struct.memory_guarantee_remaining = iprot.readDouble();
              struct.set_memory_guarantee_remaining_isSet(true);
            } else { 
              org.apache.storm.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type);
            }
            break;
          case 10: // CPU_GUARANTEE_REMAINING
            if (schemeField.type == org.apache.storm.thrift.protocol.TType.DOUBLE) {
              struct.cpu_guarantee_remaining = iprot.readDouble();
              struct.set_cpu_guarantee_remaining_isSet(true);
            } else { 
              org.apache.storm.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type);
            }
            break;
          case 11: // ISOLATED_NODE_GUARANTEE
            if (schemeField.type == org.apache.storm.thrift.protocol.TType.I32) {
              struct.isolated_node_guarantee = iprot.readI32();
              struct.set_isolated_node_guarantee_isSet(true);
            } else { 
              org.apache.storm.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type);
            }
            break;
          case 12: // TOTAL_TASKS
            if (schemeField.type == org.apache.storm.thrift.protocol.TType.I32) {
              struct.total_tasks = iprot.readI32();
              struct.set_total_tasks_isSet(true);
            } else { 
              org.apache.storm.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type);
            }
            break;
          case 13: // REQUESTED_ON_HEAP_MEMORY
            if (schemeField.type == org.apache.storm.thrift.protocol.TType.DOUBLE) {
              struct.requested_on_heap_memory = iprot.readDouble();
              struct.set_requested_on_heap_memory_isSet(true);
            } else { 
              org.apache.storm.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type);
            }
            break;
          case 14: // REQUESTED_OFF_HEAP_MEMORY
            if (schemeField.type == org.apache.storm.thrift.protocol.TType.DOUBLE) {
              struct.requested_off_heap_memory = iprot.readDouble();
              struct.set_requested_off_heap_memory_isSet(true);
            } else { 
              org.apache.storm.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type);
            }
            break;
          case 15: // REQUESTED_TOTAL_MEMORY
            if (schemeField.type == org.apache.storm.thrift.protocol.TType.DOUBLE) {
              struct.requested_total_memory = iprot.readDouble();
              struct.set_requested_total_memory_isSet(true);
            } else { 
              org.apache.storm.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type);
            }
            break;
          case 16: // REQUESTED_CPU
            if (schemeField.type == org.apache.storm.thrift.protocol.TType.DOUBLE) {
              struct.requested_cpu = iprot.readDouble();
              struct.set_requested_cpu_isSet(true);
            } else { 
              org.apache.storm.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type);
            }
            break;
          case 17: // ASSIGNED_ON_HEAP_MEMORY
            if (schemeField.type == org.apache.storm.thrift.protocol.TType.DOUBLE) {
              struct.assigned_on_heap_memory = iprot.readDouble();
              struct.set_assigned_on_heap_memory_isSet(true);
            } else { 
              org.apache.storm.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type);
            }
            break;
          case 18: // ASSIGNED_OFF_HEAP_MEMORY
            if (schemeField.type == org.apache.storm.thrift.protocol.TType.DOUBLE) {
              struct.assigned_off_heap_memory = iprot.readDouble();
              struct.set_assigned_off_heap_memory_isSet(true);
            } else { 
              org.apache.storm.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type);
            }
            break;
          default:
            org.apache.storm.thrift.protocol.TProtocolUtil.skip(iprot, schemeField.type);
        }
        iprot.readFieldEnd();
      }
      iprot.readStructEnd();
      struct.validate();
    }

    public void write(org.apache.storm.thrift.protocol.TProtocol oprot, OwnerResourceSummary struct) throws org.apache.storm.thrift.TException {
      struct.validate();

      oprot.writeStructBegin(STRUCT_DESC);
      if (struct.owner != null) {
        oprot.writeFieldBegin(OWNER_FIELD_DESC);
        oprot.writeString(struct.owner);
        oprot.writeFieldEnd();
      }
      if (struct.is_set_total_topologies()) {
        oprot.writeFieldBegin(TOTAL_TOPOLOGIES_FIELD_DESC);
        oprot.writeI32(struct.total_topologies);
        oprot.writeFieldEnd();
      }
      if (struct.is_set_total_executors()) {
        oprot.writeFieldBegin(TOTAL_EXECUTORS_FIELD_DESC);
        oprot.writeI32(struct.total_executors);
        oprot.writeFieldEnd();
      }
      if (struct.is_set_total_workers()) {
        oprot.writeFieldBegin(TOTAL_WORKERS_FIELD_DESC);
        oprot.writeI32(struct.total_workers);
        oprot.writeFieldEnd();
      }
      if (struct.is_set_memory_usage()) {
        oprot.writeFieldBegin(MEMORY_USAGE_FIELD_DESC);
        oprot.writeDouble(struct.memory_usage);
        oprot.writeFieldEnd();
      }
      if (struct.is_set_cpu_usage()) {
        oprot.writeFieldBegin(CPU_USAGE_FIELD_DESC);
        oprot.writeDouble(struct.cpu_usage);
        oprot.writeFieldEnd();
      }
      if (struct.is_set_memory_guarantee()) {
        oprot.writeFieldBegin(MEMORY_GUARANTEE_FIELD_DESC);
        oprot.writeDouble(struct.memory_guarantee);
        oprot.writeFieldEnd();
      }
      if (struct.is_set_cpu_guarantee()) {
        oprot.writeFieldBegin(CPU_GUARANTEE_FIELD_DESC);
        oprot.writeDouble(struct.cpu_guarantee);
        oprot.writeFieldEnd();
      }
      if (struct.is_set_memory_guarantee_remaining()) {
        oprot.writeFieldBegin(MEMORY_GUARANTEE_REMAINING_FIELD_DESC);
        oprot.writeDouble(struct.memory_guarantee_remaining);
        oprot.writeFieldEnd();
      }
      if (struct.is_set_cpu_guarantee_remaining()) {
        oprot.writeFieldBegin(CPU_GUARANTEE_REMAINING_FIELD_DESC);
        oprot.writeDouble(struct.cpu_guarantee_remaining);
        oprot.writeFieldEnd();
      }
      if (struct.is_set_isolated_node_guarantee()) {
        oprot.writeFieldBegin(ISOLATED_NODE_GUARANTEE_FIELD_DESC);
        oprot.writeI32(struct.isolated_node_guarantee);
        oprot.writeFieldEnd();
      }
      if (struct.is_set_total_tasks()) {
        oprot.writeFieldBegin(TOTAL_TASKS_FIELD_DESC);
        oprot.writeI32(struct.total_tasks);
        oprot.writeFieldEnd();
      }
      if (struct.is_set_requested_on_heap_memory()) {
        oprot.writeFieldBegin(REQUESTED_ON_HEAP_MEMORY_FIELD_DESC);
        oprot.writeDouble(struct.requested_on_heap_memory);
        oprot.writeFieldEnd();
      }
      if (struct.is_set_requested_off_heap_memory()) {
        oprot.writeFieldBegin(REQUESTED_OFF_HEAP_MEMORY_FIELD_DESC);
        oprot.writeDouble(struct.requested_off_heap_memory);
        oprot.writeFieldEnd();
      }
      if (struct.is_set_requested_total_memory()) {
        oprot.writeFieldBegin(REQUESTED_TOTAL_MEMORY_FIELD_DESC);
        oprot.writeDouble(struct.requested_total_memory);
        oprot.writeFieldEnd();
      }
      if (struct.is_set_requested_cpu()) {
        oprot.writeFieldBegin(REQUESTED_CPU_FIELD_DESC);
        oprot.writeDouble(struct.requested_cpu);
        oprot.writeFieldEnd();
      }
      if (struct.is_set_assigned_on_heap_memory()) {
        oprot.writeFieldBegin(ASSIGNED_ON_HEAP_MEMORY_FIELD_DESC);
        oprot.writeDouble(struct.assigned_on_heap_memory);
        oprot.writeFieldEnd();
      }
      if (struct.is_set_assigned_off_heap_memory()) {
        oprot.writeFieldBegin(ASSIGNED_OFF_HEAP_MEMORY_FIELD_DESC);
        oprot.writeDouble(struct.assigned_off_heap_memory);
        oprot.writeFieldEnd();
      }
      oprot.writeFieldStop();
      oprot.writeStructEnd();
    }

  }

  private static class OwnerResourceSummaryTupleSchemeFactory implements org.apache.storm.thrift.scheme.SchemeFactory {
    public OwnerResourceSummaryTupleScheme getScheme() {
      return new OwnerResourceSummaryTupleScheme();
    }
  }

  private static class OwnerResourceSummaryTupleScheme extends org.apache.storm.thrift.scheme.TupleScheme<OwnerResourceSummary> {

    @Override
    public void write(org.apache.storm.thrift.protocol.TProtocol prot, OwnerResourceSummary struct) throws org.apache.storm.thrift.TException {
      org.apache.storm.thrift.protocol.TTupleProtocol oprot = (org.apache.storm.thrift.protocol.TTupleProtocol) prot;
      oprot.writeString(struct.owner);
      java.util.BitSet optionals = new java.util.BitSet();
      if (struct.is_set_total_topologies()) {
        optionals.set(0);
      }
      if (struct.is_set_total_executors()) {
        optionals.set(1);
      }
      if (struct.is_set_total_workers()) {
        optionals.set(2);
      }
      if (struct.is_set_memory_usage()) {
        optionals.set(3);
      }
      if (struct.is_set_cpu_usage()) {
        optionals.set(4);
      }
      if (struct.is_set_memory_guarantee()) {
        optionals.set(5);
      }
      if (struct.is_set_cpu_guarantee()) {
        optionals.set(6);
      }
      if (struct.is_set_memory_guarantee_remaining()) {
        optionals.set(7);
      }
      if (struct.is_set_cpu_guarantee_remaining()) {
        optionals.set(8);
      }
      if (struct.is_set_isolated_node_guarantee()) {
        optionals.set(9);
      }
      if (struct.is_set_total_tasks()) {
        optionals.set(10);
      }
      if (struct.is_set_requested_on_heap_memory()) {
        optionals.set(11);
      }
      if (struct.is_set_requested_off_heap_memory()) {
        optionals.set(12);
      }
      if (struct.is_set_requested_total_memory()) {
        optionals.set(13);
      }
      if (struct.is_set_requested_cpu()) {
        optionals.set(14);
      }
      if (struct.is_set_assigned_on_heap_memory()) {
        optionals.set(15);
      }
      if (struct.is_set_assigned_off_heap_memory()) {
        optionals.set(16);
      }
      oprot.writeBitSet(optionals, 17);
      if (struct.is_set_total_topologies()) {
        oprot.writeI32(struct.total_topologies);
      }
      if (struct.is_set_total_executors()) {
        oprot.writeI32(struct.total_executors);
      }
      if (struct.is_set_total_workers()) {
        oprot.writeI32(struct.total_workers);
      }
      if (struct.is_set_memory_usage()) {
        oprot.writeDouble(struct.memory_usage);
      }
      if (struct.is_set_cpu_usage()) {
        oprot.writeDouble(struct.cpu_usage);
      }
      if (struct.is_set_memory_guarantee()) {
        oprot.writeDouble(struct.memory_guarantee);
      }
      if (struct.is_set_cpu_guarantee()) {
        oprot.writeDouble(struct.cpu_guarantee);
      }
      if (struct.is_set_memory_guarantee_remaining()) {
        oprot.writeDouble(struct.memory_guarantee_remaining);
      }
      if (struct.is_set_cpu_guarantee_remaining()) {
        oprot.writeDouble(struct.cpu_guarantee_remaining);
      }
      if (struct.is_set_isolated_node_guarantee()) {
        oprot.writeI32(struct.isolated_node_guarantee);
      }
      if (struct.is_set_total_tasks()) {
        oprot.writeI32(struct.total_tasks);
      }
      if (struct.is_set_requested_on_heap_memory()) {
        oprot.writeDouble(struct.requested_on_heap_memory);
      }
      if (struct.is_set_requested_off_heap_memory()) {
        oprot.writeDouble(struct.requested_off_heap_memory);
      }
      if (struct.is_set_requested_total_memory()) {
        oprot.writeDouble(struct.requested_total_memory);
      }
      if (struct.is_set_requested_cpu()) {
        oprot.writeDouble(struct.requested_cpu);
      }
      if (struct.is_set_assigned_on_heap_memory()) {
        oprot.writeDouble(struct.assigned_on_heap_memory);
      }
      if (struct.is_set_assigned_off_heap_memory()) {
        oprot.writeDouble(struct.assigned_off_heap_memory);
      }
    }

    @Override
    public void read(org.apache.storm.thrift.protocol.TProtocol prot, OwnerResourceSummary struct) throws org.apache.storm.thrift.TException {
      org.apache.storm.thrift.protocol.TTupleProtocol iprot = (org.apache.storm.thrift.protocol.TTupleProtocol) prot;
      struct.owner = iprot.readString();
      struct.set_owner_isSet(true);
      java.util.BitSet incoming = iprot.readBitSet(17);
      if (incoming.get(0)) {
        struct.total_topologies = iprot.readI32();
        struct.set_total_topologies_isSet(true);
      }
      if (incoming.get(1)) {
        struct.total_executors = iprot.readI32();
        struct.set_total_executors_isSet(true);
      }
      if (incoming.get(2)) {
        struct.total_workers = iprot.readI32();
        struct.set_total_workers_isSet(true);
      }
      if (incoming.get(3)) {
        struct.memory_usage = iprot.readDouble();
        struct.set_memory_usage_isSet(true);
      }
      if (incoming.get(4)) {
        struct.cpu_usage = iprot.readDouble();
        struct.set_cpu_usage_isSet(true);
      }
      if (incoming.get(5)) {
        struct.memory_guarantee = iprot.readDouble();
        struct.set_memory_guarantee_isSet(true);
      }
      if (incoming.get(6)) {
        struct.cpu_guarantee = iprot.readDouble();
        struct.set_cpu_guarantee_isSet(true);
      }
      if (incoming.get(7)) {
        struct.memory_guarantee_remaining = iprot.readDouble();
        struct.set_memory_guarantee_remaining_isSet(true);
      }
      if (incoming.get(8)) {
        struct.cpu_guarantee_remaining = iprot.readDouble();
        struct.set_cpu_guarantee_remaining_isSet(true);
      }
      if (incoming.get(9)) {
        struct.isolated_node_guarantee = iprot.readI32();
        struct.set_isolated_node_guarantee_isSet(true);
      }
      if (incoming.get(10)) {
        struct.total_tasks = iprot.readI32();
        struct.set_total_tasks_isSet(true);
      }
      if (incoming.get(11)) {
        struct.requested_on_heap_memory = iprot.readDouble();
        struct.set_requested_on_heap_memory_isSet(true);
      }
      if (incoming.get(12)) {
        struct.requested_off_heap_memory = iprot.readDouble();
        struct.set_requested_off_heap_memory_isSet(true);
      }
      if (incoming.get(13)) {
        struct.requested_total_memory = iprot.readDouble();
        struct.set_requested_total_memory_isSet(true);
      }
      if (incoming.get(14)) {
        struct.requested_cpu = iprot.readDouble();
        struct.set_requested_cpu_isSet(true);
      }
      if (incoming.get(15)) {
        struct.assigned_on_heap_memory = iprot.readDouble();
        struct.set_assigned_on_heap_memory_isSet(true);
      }
      if (incoming.get(16)) {
        struct.assigned_off_heap_memory = iprot.readDouble();
        struct.set_assigned_off_heap_memory_isSet(true);
      }
    }
  }

  private static <S extends org.apache.storm.thrift.scheme.IScheme> S scheme(org.apache.storm.thrift.protocol.TProtocol proto) {
    return (org.apache.storm.thrift.scheme.StandardScheme.class.equals(proto.getScheme()) ? STANDARD_SCHEME_FACTORY : TUPLE_SCHEME_FACTORY).getScheme();
  }
}

