Re: limit of lines?

From: Joanna Carter \(TeamB\) (joanna_at_nospam.co.uk)
Date: 01/03/05


Date: Mon, 3 Jan 2005 17:12:41 -0000


"Roman Kaßebaum" <roman.kassebaumnospam@kdv-dt.de> a écrit dans le message
de news: 41d924be$1@newsgroups.borland.com...

> Please, post a quick example.

Copied from an older post
///////////////////////////////////
First, you need a simple metadata type...

  IMetadata = interface
  [GUID]
    function GetName: string;
    function GetType: TValueTypeType;
  end;

...then you can add type specific additional data...

  IStringMetadata = interface(IMetadata)
  [GUID]
    function GetLength: Integer;
    function GetCase: TStringCase;
  end;

  IFloatMetadata = interface(IMetadata)
  [GUID]
    function GetSize: Integer;
    function GetPrecision: Integer;
  end;

Then comes the main Value Type types from which all business objects are
built...

  IValueType = interface
  [GUID]
    procedure Assign(const Other: IValueType);
    function Clone: IValueType;
    function GetAsString: string;
    function GetFormatString: string;
    function GetMetadata: IMetadata;
    function GetName: string;
    function GetRequired: Boolean;
    function IsNull: Boolean;
    procedure SetAsString(const Value: string);
    procedure SetFormatString(const Value: string);
    procedure SetNull;
    procedure SetRequired(Value: Boolean);
    property AsString: string
             read GetAsString
             write SetAsString;
    property FormatString: string
             read GetFormatString
             write SetFormatString;
    property Required: Boolean
             read GetRequired
             write SetRequired;
  end;

Once again, we can add type specific information to the generic case.

e.g.

  IIntegerValueType = interface(IValueType)
  [GUID]
    function GetValue: Integer;
    procedure SetValue(Value: Integer);
    property Value: Integer
             read GetValue
             write SetValue;
  end;

  IStringValueType = interface(IValueType)
  [GUID]
    function GetValue: string;
    procedure SetValue(const Value: string);
    property Value: string
             read GetValue
             write SetValue;
  end;

All Business Objects that contain properties/attributes are derived from
IObjectValueType, which is designed to contain a list of Value Types, one
for each property about which you wish to obtain metadata...

  IObjectValueType = interface(IValueType)
  [GUID]
    function GetValueType(const Name: string): IValueType;
    function GetValueTypes: IValueTypeList;
    function GetType: TGUID;
    function GetValue: IInterface;
    property Value: IInterface
             read GetValue;
  end;

Finally, you can build something like a Customer interface and class...

  ICustomer = interface
  [GUID]
    function GetCode: string;
    function GetName: string;
    function GetTotalOnOrder: Double;
    function GetTotalShipped: Double;
    procedure SetCode(const Value: string);
    procedure SetName(const Value: string);
    procedure SetTotalOnOrder(Value: Double);
    procedure SetTotalShipped(Value: Double);
    property Code: string
             read GetCode
             write SetCode;
    property Name: string
             read GetName
             write SetName;
    property TotalOnOrder: Double
             read GetTotalOnOrder
             write SetTotalOnOrder;
    property TotalShipped: Double
             read GetTotalShipped
             write SetTotalShipped;
  end;

  TCustomer = class(TObjectValueType, ICustomer)
  private
    // ICustomer
    function GetCode: string;
    function GetName: string;
    function GetTotalOnOrder: Double;
    function GetTotalShipped: Double;
    procedure SetCode(const Value: string);
    procedure SetName(const Value: string);
    procedure SetTotalOnOrder(Value: Double);
    procedure SetTotalShipped(Value: Double);
  end;

Property accessors usually look like this...

function TCustomer.GetName: string;
begin
  Result := (GetValueTypes['Name'] as IStringValueType).Value;
end;

procedure TCustomer.SetName(const Value: string);
begin
  (GetValueTypes['Name'] as IStringValueType).Value := Value;
end;

This structure allows you to address the properties of an ICustomer as
simple properties, but also as the sub value types of an object value type
complete with all their metadata.

Normal code uses the ICustomer interface, whilst OPFs and MVP frameworks can
make use of the Value Type information for persistence and display
purposes - much more sophisticated than 'data-aware'. :-))
/////////////////////////////////////

> I mean that fireing a sql for every object is slower than fireing one
> sql for all objects.

Not if the SQL for a join returns more rows of more columns.

e.g. to return a single set that encompasses a typical Order/Lines scenario,
you could do :

SELECT * FROM order, orderline WHERE order.ID = orderline.ID;

This will bring back all the columns for Order as well as all the columns
for every Order Line. If we say 5 columns for the Order and 5 Columns for
the Line, bringing back 100 Orders with 10 lines each will return 10,000
'cells'.

Now we do :

SELECT ID, OrderRef FROM order

This brings back 200 'cells' for the dsame 100 Orders and is sufficient to
allow a user to browse the list of Orders and choose one according to the
OrderRef.

next we do :

SELECT * FROM order WHERE ID = <id of chosen object in list>

followed by an 'internal' SELECT * FROM orderline where ID = <id of chosen
order>

to load up the lines for the selected Order. These two SQL statements should
be executed in the same transaction, thus avoiding twice the start/stop
overhead.

This brings back 5 cells for the Order and 5 cells for each of the related
Line items; if the Order has 10 lines, then this returns an additional 50
cells.

In total, 255 'cells' have been returned to get one Order into a state where
it can be edited. Of course these numbers are relatively small, so you can
imagine the ration of improvement with larger records and tables.

It is unusual to require all the properties of all the objects in a
collection just to choose one object to edit. It is minimising the number of
columns returned for browsing that keeps the performance up, only loading
complete objects as and when they are edited, and even then only loading
complex object properties as and when they are accessed.

In the OO world we don't have to put up with loading full width multi-table
joins all at the same time, we can optimize the volume of data returned and
thereby, sometimes, even exceed the efficiency of some traditional database
driven apps.

Joanna

--
Joanna Carter (TeamB)
Consultant Software Engineer
TeamBUG support for UK-BUG
TeamMM support for ModelMaker


Relevant Pages

  • Re: .NET COM/ActiveX problem
    ... but I changed it to string GUIDs and converted it to Guids on the impl side ... Manufacturer, _bstr_t Model, GUID MyMethod) ... public interface IMyHostWnd ... Then the impl: ...
    (microsoft.public.dotnet.framework)
  • Re: classes/ interface/device-setup/etc
    ... the guid in is the setup class, typically an INF will have nothing ... >>> I have a very unique device that needs an interface class of its own. ... They register the same GUID. ...
    (microsoft.public.development.device.drivers)
  • Re: classes/ interface/device-setup/etc
    ... > I have a very unique device that needs an interface class of its own. ... They register the same GUID. ... > And where does the [ClassInstall32] section of the .inf file fit into ... this set display name of class and icon - As icon I use standard usb icon. ...
    (microsoft.public.development.device.drivers)
  • Re: IConnectionPointContainer & C#
    ... interface proxy marshalling, and I'm not surprized that something is getting ... void IConnectionPointContainer.FindConnectionPoint(ref Guid riid, out ... IConnectionPoint ppCP) ... But the COM client that gets this IConnectionPoint ...
    (microsoft.public.dotnet.languages.csharp)
  • Re: use createfile to access usb device
    ... GUID_DEVCLAS_USB is a device class. ... Not all USB devices have the same interface, ... If you don't know the device interface GUID for the ... >> SetupDiEnumDeviceInterfaces() and SetupDiGetDeviceInterfaceDetail. ...
    (microsoft.public.development.device.drivers)