// 
// Decompiled by Procyon v0.6.0
// 

package com.google.common.flogger;

import java.util.Iterator;
import com.google.common.flogger.util.Checks;

public class MetadataKey<T>
{
    private final String label;
    private final Class<? extends T> clazz;
    private final boolean canRepeat;
    private final long bloomFilterMask;
    
    public static <T> MetadataKey<T> single(final String label, final Class<? extends T> clazz) {
        return new MetadataKey<T>(label, clazz, false);
    }
    
    public static <T> MetadataKey<T> repeated(final String label, final Class<T> clazz) {
        return new MetadataKey<T>(label, (Class<? extends T>)clazz, true);
    }
    
    protected MetadataKey(final String label, final Class<? extends T> clazz, final boolean canRepeat) {
        this.label = Checks.checkMetadataIdentifier(label);
        this.clazz = Checks.checkNotNull(clazz, "class");
        this.canRepeat = canRepeat;
        this.bloomFilterMask = this.createBloomFilterMaskFromSystemHashcode();
    }
    
    public final String getLabel() {
        return this.label;
    }
    
    public final T cast(final Object value) {
        return (T)this.clazz.cast(value);
    }
    
    public final boolean canRepeat() {
        return this.canRepeat;
    }
    
    public void emit(final T value, final KeyValueHandler out) {
        out.handle(this.getLabel(), value);
    }
    
    public void emitRepeated(final Iterator<T> values, final KeyValueHandler out) {
        Checks.checkState(this.canRepeat, "non repeating key");
        while (values.hasNext()) {
            this.emit(values.next(), out);
        }
    }
    
    public final long getBloomFilterMask() {
        return this.bloomFilterMask;
    }
    
    @Override
    public final int hashCode() {
        return super.hashCode();
    }
    
    @Override
    public final boolean equals(final Object obj) {
        return super.equals(obj);
    }
    
    @Override
    public final String toString() {
        return this.getClass().getName() + "/" + this.label + "[" + this.clazz.getName() + "]";
    }
    
    private long createBloomFilterMaskFromSystemHashcode() {
        int hash = System.identityHashCode(this);
        long bloom = 0L;
        for (int n = 0; n < 5; ++n) {
            bloom |= 1L << (hash & 0x3F);
            hash >>>= 6;
        }
        return bloom;
    }
    
    public interface KeyValueHandler
    {
        void handle(final String p0, final Object p1);
    }
}
