Note that there are some explanatory texts on larger screens.

plurals
  1. PO
    primarykey
    data
    text
    <p>Not sure what you want to use this for, or whether it's worth the trouble, but the implementations I've seen in this thread so far all have the problem that the alias becomes disconnected from the key it's aliasing. For instance, if you say:</p> <pre><code>SuperMap&lt;String, String&gt; sm = new SuperMap&lt;String, String&gt;(); sm.put("Elvis", "Presley"); sm.addAlias("Priscilla", "Elvis"); System.out.println(sm.get("Elvis")); System.out.println(sm.get("Priscilla")); sm.put("Elvis", "Costello"); System.out.println(sm.get("Elvis")); System.out.println(sm.get("Priscilla")); </code></pre> <p>you're going to get:</p> <pre><code>Presley Presley Costello Presley </code></pre> <p><em>(Note: that's with the original implementation of <a href="https://stackoverflow.com/a/15486966/27358">SuperMap</a>, not the edited version.)</em></p> <p>If you want a true alias -- if you want to get <code>Presley, Presley, Costello, Costello</code> -- you're going to need something a little more complicated.</p> <p>The code below is untested (and the whole enterprise seems a little bit insane), but something like it should work:</p> <pre><code>public class AliasMap&lt;K, V&gt; extends AbstractMap&lt;K, V&gt; { private final Map&lt;K, V&gt; backingMap; private final Map&lt;K, K&gt; aliasToRealKey; public AliasMap () { this( new HashMap&lt;K, V&gt;() ); } public AliasMap ( Map&lt;K, V&gt; backingMap ) { this.backingMap = backingMap; aliasToRealKey = new HashMap&lt;K, K&gt;(); } @Override public Set&lt;Entry&lt;K, V&gt;&gt; entrySet () { return new AliasAwareEntrySet&lt;K, V&gt;( aliasToRealKey, backingMap ); } @Override public V put ( K k, V v ) { if ( aliasToRealKey.containsKey( k ) ) { throw new IllegalArgumentException( "An alias '" + k + "' already exists in the map" ); } return backingMap.put( k, v ); } @Override public V get ( Object o ) { V v = backingMap.get( o ); if ( v == null ) { K realKey = aliasToRealKey.get( o ); if ( realKey == null ) { return null; } return backingMap.get( realKey ); } return v; } public void alias ( K realKey, K alias ) { if ( backingMap.containsKey( alias ) ) { throw new IllegalArgumentException( "The key '" + alias + "' already exists in the map" ); } aliasToRealKey.put( alias, realKey ); } private static class AliasAwareEntrySet&lt;K, V&gt; extends AbstractSet&lt;Entry&lt;K, V&gt;&gt; { private Map&lt;K, K&gt; aliasToRealKey; private Map&lt;K, V&gt; backingMap; public AliasAwareEntrySet ( Map&lt;K, K&gt; aliasToRealKey, final Map&lt;K, V&gt; backingMap ) { this.aliasToRealKey = aliasToRealKey; this.backingMap = backingMap; } @Override public Iterator&lt;Entry&lt;K, V&gt;&gt; iterator () { return new AliasAwareEntryIterator&lt;K, V&gt;( backingMap, aliasToRealKey ); } @Override public int size () { return backingMap.size() + aliasToRealKey.size(); } } private static class AliasAwareEntryIterator&lt;K, V&gt; implements Iterator&lt;Entry&lt;K, V&gt;&gt; { Set&lt;Entry&lt;K, V&gt;&gt; realEntries; Set&lt;K&gt; aliasKeys; Iterator&lt;Entry&lt;K, V&gt;&gt; realIterator; Iterator&lt;K&gt; aliasIterator; boolean isRealEntry = true; private Map&lt;K, V&gt; backingMap; private Map&lt;K, K&gt; aliasToRealKey; public AliasAwareEntryIterator ( final Map&lt;K, V&gt; backingMap, Map&lt;K, K&gt; aliasToRealKey ) { this.realEntries = backingMap.entrySet(); this.aliasKeys = aliasToRealKey.keySet(); realIterator = realEntries.iterator(); aliasIterator = aliasKeys.iterator(); this.backingMap = backingMap; this.aliasToRealKey = aliasToRealKey; } public boolean hasNext () { return realIterator.hasNext() || aliasIterator.hasNext(); } public Entry&lt;K, V&gt; next () { if ( realIterator.hasNext() ) { return realIterator.next(); } isRealEntry = false; final K alias = aliasIterator.next(); final K realKey = aliasToRealKey.get( alias ); return new AliasAwareEntry( alias, realKey ); } public void remove () { if ( isRealEntry ) { realIterator.remove(); } else { aliasIterator.remove(); } } private class AliasAwareEntry implements Entry&lt;K, V&gt; { private final K alias; private final K realKey; public AliasAwareEntry ( K alias, K realKey ) { this.alias = alias; this.realKey = realKey; } public K getKey () { return alias; } public V getValue () { return backingMap.get( realKey ); } public V setValue ( V v ) { return backingMap.put( realKey, v ); } } } public static void main ( String[] args ) { AliasMap&lt;String, String&gt; sm = new AliasMap&lt;String, String&gt;(); sm.put( "Elvis", "Presley" ); sm.alias( "Elvis", "Priscilla" ); System.out.println( sm.get( "Elvis" ) ); System.out.println( sm.get( "Priscilla" ) ); sm.put( "Elvis", "Costello" ); System.out.println( sm.get( "Elvis" ) ); System.out.println( sm.get( "Priscilla" ) ); for ( String s : sm.keySet() ) { System.out.println(s); } for ( Iterator&lt;Entry&lt;String, String&gt;&gt; iterator = sm.entrySet().iterator(); iterator.hasNext(); ) { Entry&lt;String, String&gt; entry = iterator.next(); System.out.println( entry.getKey() + " : " + entry.getValue() ); if ( "Priscilla".equals( entry.getKey() ) ) { iterator.remove(); } } for ( String s : sm.keySet() ) { System.out.println(s); } } } </code></pre>
    singulars
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. VO
      singulars
      1. This table or related slice is empty.
    2. VO
      singulars
      1. This table or related slice is empty.
    3. VO
      singulars
      1. This table or related slice is empty.
    1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload