代理模式

Posted wskxy

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了代理模式相关的知识,希望对你有一定的参考价值。

1.简介

  代理模式给某一个对象提供一个代理对象,并由代理对象控制对原对象的引用。通俗的来讲代理模式就是我们生活中常见的中介。

  可以做:日志代理、缓存代理、异常代理、延迟代理、权限代理、单例代理

2.一个简单的代理模式例子

  我们模拟人们购票环节,一个人买车票得自己坐车去车站排队购票

  如果有一个代理人帮我们去购票,我们只需要寻找这个代理人,而不需要去火车站

  添加一个接口ISuject(凡是涉及相同操作的类,最好都继承一个接口,这样在调用的时候可以使用抽象接口来定义,避免使用具体类)

namespace ProxyPattern
{
    interface ISubject
    {
        bool GetSomething();
        void DoSomething();
    }
}

  添加一个真实购票类RealSubject

namespace ProxyPattern
{
    class RealSubject:ISubject
    {
        public RealSubject()
        {
            Console.WriteLine("RealSubject开始构造");
            Console.WriteLine("耗时");
            Console.WriteLine("RealSubject构造完成");
        }
        public bool GetSomething()
        {
            Console.WriteLine("坐车去火车站看余票。。。");
            Console.WriteLine("耗时");
            Console.WriteLine("到车站看到有票。。。");
            return true;
        }
        public void DoSomething()
        {
            Console.WriteLine("开始排队。。。");
            Console.WriteLine("耗时");
            Console.WriteLine("买到票了。。。");
        }
    }
}

  添加一个代理类ProxySubject

namespace ProxyPattern
{
    class ProxySubject : ISubject
    {
        /// <summary>
        /// 定义一个代理
        /// </summary>
        private ISubject _subject = new RealSubject();
        public bool GetSomething()
        {
            return _subject.GetSomething();
        }
        public void DoSomething()
        {
            _subject.DoSomething();
        }
    }
}

  Program:

namespace ProxyPattern
{
    class Program
    {
        static void Main(string[] args)
        {
            ISubject subject = new ProxySubject();
            subject.GetSomething();
            subject.DoSomething();
            Console.Read();
        }
    }
}

  在Program中我们只调用了代理类,通过代理类去帮我们实现操作(也就是常说的加一层)

3.日志代理

  在很多时候RealSubject可能涉及复杂的逻辑结构,在这里面加日志明显并不方便,所以我们可以使用日志代理,实现日志功能

namespace ProxyPattern
{
    class ProxySubject : ISubject
    {
        private ISubject _subject = new RealSubject();
        public bool GetSomething()
        {
            try
            {
                Console.WriteLine("日志:GetSomething开始执行");
                bool result = _subject.GetSomething();
                Console.WriteLine("日志:GetSomething执行结束");
                return result;
            }
            catch (Exception ex)
            {
                Console.WriteLine("日志:GetSomething执行出错");
                return false;
            }
        }
        public void DoSomething()
        {
            try
            {
                Console.WriteLine("日志:DoSomething开始执行");
                _subject.DoSomething();
                Console.WriteLine("日志:DoSomething执行结束");
            }
            catch(Exception ex)
            {
                Console.WriteLine("日志:DoSomething执行出错");
            }
        }
    }
}

4.缓存代理

  定义一个静态对象保存缓存

namespace ProxyPattern
{
    class ProxySubject : ISubject
    {
        private ISubject _subject = new RealSubject();
        //0 表示代理人还没到火车站  1表示代理人已经到了火车站,不需要再调用GetSomething
        //相当于保存一个缓存
        static int GetSomethingResult = 0;
        public bool GetSomething()
        {
            if(GetSomethingResult ==0)
            { 
                bool result = _subject.GetSomething();
                GetSomethingResult = 1;
                return result;
            }
            else
            {
                return true;
            }
        }
        public void DoSomething()
        {
            _subject.DoSomething();
        }
    }
}

 5.延迟代理

namespace ProxyPattern
{
    class ProxySubject : ISubject
    {
        private ISubject _subject = null;
        public bool GetSomething()
        {
            if(_subject==null)//把实例化延迟到调用的时候再使用
            {
                _subject = new RealSubject();
            }
            bool result = _subject.GetSomething();
            return result;
        }
        public void DoSomething()
        {
            _subject.DoSomething();
        }
    }
}

 

以上是关于代理模式的主要内容,如果未能解决你的问题,请参考以下文章

scrapy按顺序启动多个爬虫代码片段(python3)

用于从 cloudkit 检索单列的代码模式/片段

java代码实现设计模式之代理模式

代理模式(静态代理动态代理)代码实战(详细)

Java设计模式-代理模式之动态代理(附源代码分析)

代理模式(静态代理)