For faster navigation, this Iframe is preloading the Wikiwand page for 享元模式.

享元模式

本条目存在以下问题,请协助改善本条目或在讨论页针对议题发表看法。 此条目需要精通或熟悉相关主题的编者参与及协助编辑。 (2014年10月6日)请邀请适合的人士改善本条目。更多的细节与详情请参见讨论页。 此条目没有列出任何参考或来源。 (2014年10月6日)维基百科所有的内容都应该可供查证。请协助补充可靠来源改善这篇条目。无法查证的内容可能会因为异议提出而被移除。 此条目已列出参考文献,但因为没有文内引注而使来源仍然不明。 (2010年5月12日)请加上合适的文内引注来改善这篇条目

享元模式(英语:Flyweight Pattern)是一种软件设计模式。它使用物件用来尽可能减少内存使用量;于相似物件中分享尽可能多的资讯。当大量物件近乎重复方式存在,因而使用大量内存时,此法适用。通常物件中的部分状态(state)能够共享。常见做法是把它们放在数据结构外部,当需要使用时再将它们传递给享元。

典型的享元模式的例子为文书处理器中以图形结构来表示字符。一个做法是,每个字形有其字型外观, 字模 metrics, 和其它格式资讯,但这会使每个字符就耗用上千字节。取而代之的是,每个字符参照到一个共享字形物件,此物件会被其它有共同特质的字符所分享;只有每个字符(文件中或页面中)的位置才需要另外储存。

示例

[编辑]

以下程式用来解释上述的文字。这个例子用来解释享元模式利用只加载执行任务时所必需的最少资料,因而减少内存使用量。

public enum FontEffect {
    BOLD, ITALIC, SUPERSCRIPT, SUBSCRIPT, STRIKETHROUGH
}

public final class FontData {
    /**
     * A weak hash map will drop unused references to FontData.
     * Values have to be wrapped in WeakReferences, 
     * because value objects in weak hash map are held by strong references.
     */
    private static final WeakHashMap<FontData, WeakReference<FontData>> FLY_WEIGHT_DATA =
        new WeakHashMap<FontData, WeakReference<FontData>>();
    private final int pointSize;
    private final String fontFace;
    private final Color color;
    private final Set<FontEffect> effects;

    private FontData(int pointSize, String fontFace, Color color, EnumSet<FontEffect> effects) {
        this.pointSize = pointSize;
        this.fontFace = fontFace;
        this.color = color;
        this.effects = Collections.unmodifiableSet(effects);
    }

    public static FontData create(int pointSize, String fontFace, Color color,
        FontEffect... effects) {
        EnumSet<FontEffect> effectsSet = EnumSet.noneOf(FontEffect.class);
        for (FontEffect fontEffect : effects) {
            effectsSet.add(fontEffect);
        }
        // We are unconcerned with object creation cost, we are reducing overall memory consumption
        FontData data = new FontData(pointSize, fontFace, color, effectsSet);

        // Retrieve previously created instance with the given values if it (still) exists
        WeakReference<FontData> ref = FLY_WEIGHT_DATA.get(data);
        FontData result = (ref != null) ? ref.get() : null;
        
        // Store new font data instance if no matching instance exists
        if (result == null) {
            FLY_WEIGHT_DATA.put(data, new WeakReference<FontData> (data));
            result = data;
        }
        // return the single immutable copy with the given values
        return result;
    }

    @Override
    public boolean equals(Object obj) {
        if (obj instanceof FontData) {
            if (obj == this) {
                return true;
            }
            FontData other = (FontData) obj;
            return other.pointSize == pointSize && other.fontFace.equals(fontFace)
                && other.color.equals(color) && other.effects.equals(effects);
        }
        return false;
    }

    @Override
    public int hashCode() {
        return (pointSize * 37 + effects.hashCode() * 13) * fontFace.hashCode();
    }

    // Getters for the font data, but no setters. FontData is immutable.
}

外部链接

[编辑]


{{bottomLinkPreText}} {{bottomLinkText}}
享元模式
Listen to this article

This browser is not supported by Wikiwand :(
Wikiwand requires a browser with modern capabilities in order to provide you with the best reading experience.
Please download and use one of the following browsers:

This article was just edited, click to reload
This article has been deleted on Wikipedia (Why?)

Back to homepage

Please click Add in the dialog above
Please click Allow in the top-left corner,
then click Install Now in the dialog
Please click Open in the download dialog,
then click Install
Please click the "Downloads" icon in the Safari toolbar, open the first download in the list,
then click Install
{{::$root.activation.text}}

Install Wikiwand

Install on Chrome Install on Firefox
Don't forget to rate us

Tell your friends about Wikiwand!

Gmail Facebook Twitter Link

Enjoying Wikiwand?

Tell your friends and spread the love:
Share on Gmail Share on Facebook Share on Twitter Share on Buffer

Our magic isn't perfect

You can help our automatic cover photo selection by reporting an unsuitable photo.

This photo is visually disturbing This photo is not a good choice

Thank you for helping!


Your input will affect cover photo selection, along with input from other users.

X

Get ready for Wikiwand 2.0 🎉! the new version arrives on September 1st! Don't want to wait?