Control the access to an object.
The example creates first an interface against which the pattern creates the classes. This interface contains only one method to display the image, called displayImage()
, that has to be coded by all classes implementing it.
The proxy class ProxyImage
is running on another system than the real image class itself and can represent the real image RealImage
over there. The image information is accessed from the disk. Using the proxy pattern, the code of the ProxyImage
avoids multiple loading of the image, accessing it from the other system in a memory-saving manner.
using System;
namespace Proxy
{
class Program
{
interface IImage
{
void Display();
}
class RealImage : IImage
{
public RealImage(string fileName)
{
FileName = fileName;
LoadFromFile();
}
private void LoadFromFile()
{
Console.WriteLine("Loading " + FileName);
}
public String FileName { get; private set; }
public void Display()
{
Console.WriteLine("Displaying " + FileName);
}
}
class ProxyImage : IImage
{
public ProxyImage(string fileName)
{
FileName = fileName;
}
public String FileName { get; private set; }
private IImage image;
public void Display()
{
if (image == null)
image = new RealImage(FileName);
image.Display();
}
}
static void Main(string[] args)
{
IImage image = new ProxyImage("HiRes_Image");
for (int i = 0; i < 10; i++)
image.Display();
}
}
}
The program's output is:
Loading HiRes_Image Displaying HiRes_Image Displaying HiRes_Image Displaying HiRes_Image Displaying HiRes_Image Displaying HiRes_Image Displaying HiRes_Image Displaying HiRes_Image Displaying HiRes_Image Displaying HiRes_Image Displaying HiRes_Image
The following Java example illustrates the "virtual proxy" pattern. The ProxyImage
class is used to access a remote method.
interface Image {
public void displayImage();
}
//on System A
class RealImage implements Image {
private String filename = null;
/**
* Constructor
* @param aFilename
*/
public RealImage(final String aFilename) {
filename = aFilename;
loadImageFromDisk();
}
/**
* Loads the image from the disk
*/
private void loadImageFromDisk() {
System.out.println("Loading " + filename);
}
/**
* Displays the image
*/
public void displayImage() {
System.out.println("Displaying " + filename);
}
}
//on System B
class ProxyImage implements Image {
private RealImage image = null;
private String filename = null;
/**
* Constructor
* @param aFilename
*/
public ProxyImage(final String aFilename) {
filename = aFilename;
}
/**
* Displays the image
*/
public void displayImage() {
if (image == null) {
image = new RealImage(filename);
}
image.displayImage();
}
}
class ProxyExample {
/**
* Test method
*/
public static void main(String[] args) {
final Image IMAGE1 = new ProxyImage("HiRes_10MB_Photo1");
final Image IMAGE2 = new ProxyImage("HiRes_10MB_Photo2");
IMAGE1.displayImage(); // loading necessary
IMAGE1.displayImage(); // loading unnecessary
IMAGE2.displayImage(); // loading necessary
IMAGE2.displayImage(); // loading unnecessary
IMAGE1.displayImage(); // loading unnecessary
}
}
The program's output is:
Loading HiRes_10MB_Photo1 Displaying HiRes_10MB_Photo1 Displaying HiRes_10MB_Photo1 Loading HiRes_10MB_Photo2 Displaying HiRes_10MB_Photo2 Displaying HiRes_10MB_Photo2 Displaying HiRes_10MB_Photo1