расположение страницы : bookresearch.ru / Разработчику / Формирование краткой библиографической записи /

Формирование краткой библиографической записи

[ Анна Рахманина Анна Рахманина ]

При создании программного обеспечения для нужд книжного бизнеса очень часто возникает необходимость формировать в качестве описания книги правильную краткую библиографическую запись. На самом деле, это совсем не тривиальная задача, алгоритм объединения различных атрибутов описания достаточно сложен и громоздок.

В данном материале предлагается готовый код формирования такой записи по заданному набору данных (TDataSet) или по списку (TStringList) библиографических атрибутов UNIMARC. Компонент разработан для формирования записей для книг (в т.ч. CD, дисков, аудио и видеокассет) и монет.

Для формирования текстовой записи ему необходимо передать набор атрибутов описания книги (монеты) в стандарте UNIMARC. Используемое множество атрибутов указано ниже.

Пример. Рассмотрим пример использования компонента. Пусть набор данных содержит следующие записи:
ATTR_IDATTR_VALUEATTR_NAME
F010a5-87365-046-2ISBN
F210d1999Дата издания
F215c4 л. цв. ил.Другие уточнения физических характеристик
F210aМ.Место издания
F210cТролльИздатель
F200aЯпонская поэзияОсновное заглавие
F215a662Сведения о количестве страниц

Тогда нижеприведенный код вернет следующую краткую запись:
Японская поэзия. - М.: Тролль, 1999. - 662 с.: 4 л. цв. ил. - ISBN 5-87365-046-2


var
  sFullBiblioRecord: string;
begin
  ShortBiblioGenerator.FieldPrefix := 'F';
  ShortBiblioGenerator.DataSet := tblAttrValues;
  tblAttrValues.Open;
  sFullBiblioRecord :=
    ShortBiblioGenerator.Execute(tblAttrValuesATTR_ID, tblAttrValuesATTR_VALUE);
...

Исходный код компонента приведен ниже.

Untitled
{
  ===Компонент формирования краткой библиографической записи===

  Свойства, доступные через Инспектор объектов:
    FieldPrefix - префикс идентификатора поля биб. описания в передаваемом
                  наборе данных
                 (возможны разные варианты - отсутствие префикса, префикс f)
                 в случае наличия перфикса указывать обязательно для корректной
                 обработки набора данных
    DescriptionType - тип библиографического описания. Для разных типов - разные
                      краткие записи. В данной версии поддерживается формирование
                      краткой биб. записи для следующих типов:
                      dtBook - книжное описание
                      dtCoin - описание монет
    DataSet        - вертикальный набор данных                  

  Методы:
    Execute - формирует краткую библиографическую запись.

    function Execute: string;                                                   - по свойству DataSet
    function Execute(SourceDataSet: TDataSet): string;                          - по SourceDataSet
    function Execute(SourceStringList: TStringList): string;                    - по Stringlist

              В качестве вх. парметра - вертикальный набор данных
              или СтрингЛист в виде "идентификатор = значение"

  После выполнения метода Execute доступными для чтения делаются следующие свойства:
    BiblioRecord - краткая библиогрфическая запись
    BiblioHeader - заголовок краткой библиографической записи
    BiblioBody   - тело краткой библиографической записи (запись без заголовка)


    arakh & xelby, апрель 2002

}
unit gcShortBiblioGenerator;
{$I glDEF.INC}
interface

uses
  Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs, db,
  TypInfo {$IFDEF GLVER_D6}{DesignIntf, DesignEditors, VCLEditors}{$ELSE} {$IFDEF GLVER_D5},dsgnintf{$ENDIF} {$ENDIF};


type
  TDescriptionType = (dtBook, dtCoin); //???

  TShortBiblioGenerator = class(TComponent)
  private
    FFieldPrefix : string;
    FBiblioRecord: string;
    FBiblioHeader: string;
    FBiblioBody  : string;
    FDescriptionType: TDescriptionType;
    FDataSet: TDataSet;
    { Private declarations }
    procedure PrepareStringList(SourceStringList: TStringList);

  protected
    function GenerateBiblioRecord(SourceStringList: TStringList): string;
  public
    property BiblioHeader: string read FBiblioHeader;
    property BiblioBody:   string read FBiblioHeader;
    property BiblioRecord: string read FBiblioRecord;

    function Execute: string; overload;
    function Execute(SourceDataSet: TDataSet): string; overload;
    function Execute(SourceStringList: TStringList): string; overload;
  published
    property FieldPrefix: string read FFieldPrefix write FFieldPrefix;          // префикс для полей UNIMARK
    property DescriptionType: TDescriptionType read FDescriptionType write FDescriptionType default dtBook;
    property DataSet: TDataSet read FDataSet write FDataSet;
  end;
  {
  TShortBiblioGenerator_Editor = class(TComponentEditor)
    procedure ExecuteVerb(Index: Integer); override;
    function GetVerb(Index: Integer): string; override;
    function GetVerbCount: Integer; override;
  end;
  }
procedure Register;

implementation

procedure Register;
begin
  RegisterComponents('Globus Special', [TShortBiblioGenerator]);
end;

{ TShortBiblioGenerator }


function TShortBiblioGenerator.Execute: string;
begin
  // использовать родной DataSet
  Result := Execute(DataSet);
end;

function TShortBiblioGenerator.Execute(SourceDataSet: TDataSet): string;
var
  SourceStringList: TStringList;
  AttrValue       : string;
begin
  if not Assigned(SourceDataSet) then
    raise Exception.Create('Параметр DataSet не задан');

  SourceStringList := TStringList.Create;
  try
    SourceDataSet.Active := true;
    { формирование SourceStringList по DataSet }
    with SourceDataSet do
      begin
        First;
        while not eof do
          begin
            AttrValue := trim(FieldByName('attr_id').asString) + '=' + trim(FieldByName('attr_value').asString);
            SourceStringList.Add(AttrValue);
            Next;
          end;
    end;

    PrepareStringList(SourceStringList);

    Result := GenerateBiblioRecord(SourceStringList);
  finally
    SourceStringList.Free;
  end;

end;

function TShortBiblioGenerator.Execute(SourceStringList: TStringList): string;
begin
  if not Assigned(SourceStringList) then
    raise Exception.Create('Параметр StringList не задан');

  PrepareStringList(SourceStringList);

  Result := GenerateBiblioRecord(SourceStringList);
end;

{ Формирует запись по данным из StringList }
function TShortBiblioGenerator.GenerateBiblioRecord(SourceStringList: TStringList): string;

 function ValueByID(ID:string):string;
   begin
     if SourceStringList.IndexOfName(ID) <> -1 then
       result := trim(SourceStringList.Values[ID])
     else
       result := '';
   end;


var
    ch:char; // символ, который указывается в сведении о кол-ве страниц
    publ:integer;
    pls:integer;
    NumOfChar:integer; // число символов в заголовке
    slPublishers, slPlaces:TStringList;
    i,j:integer;
    F205aExists, F205Exists, F210Exists, F215aExists, F215acExists,
    F215acdExists, F215aeExists, F225aExists, F010Exists, exi : Boolean;
    Header,Body, BR: string; // заголовок, тело, полная запись


begin

//..  если исходный СтрингЛист - пустой
 if SourceStringList.Count = 0 then
   begin
     BR:='';
     Exit;
   end;

//.. создание списков для множественных значений издателей и мест идания

 slPublishers:=TStringList.Create;
 slPlaces:=TStringList.Create;
 slPublishers.Clear;
 slPlaces.Clear;


//.. инициализация переменных, нужных для формирования записи


 publ  :=0;
 BR    :='';
 ch    :='с'; // по умолчанию  - страницы
 Header:='';
 Body  :='';


if DescriptionType = dtCoin then // краткая запись для монет

begin
  BR :=ValueByID('200a');
  if BR <> '' then
    BR := BR + ' - ';
  BR := BR+ValueById('210d')+#13#10;
  Header := AnsiUpperCase(BR); //это заголовок
  NumOfChar := Length(Header);
  if ValueByID('225a') <> '' then
    BR:= BR + 'Серия: '+ValueByID('225a');
  if ValueByID('3119') <> '' then
    BR:= BR + ' Каталожный номер: ' + ValueByID('3119');
  if ValueByID('010d') <> '' then
    BR := BR + ' Номинал: ' + ValueByID('010d');
  if ((ValueByID('308a') <> '') or (ValueByID('9155') <> '')) then
    BR := BR + ' Качество: ' + ValueByID('308a') + ' ' + ValueByID('9155');
  if ValueByID('9157') <> '' then
    BR := BR + ' Вес: ' + ValueById('9157');
  if ValueByID('215d') <> '' then
    BR := BR + ' Диаметр: ' + ValueByID('215d');

  Body := copy(BR, NumOfChar+1, Length(BR)-NumOfChar);

  FBiblioRecord := BR;
  FBiblioHeader := Header;
  FBiblioBody   := Body;

  exit;
end;




if ValueById('205a') <> '' then // 205aExists
  F205aExists := true; {b10}

//если присутствуют поля F205a или F205b     // 205Exists
if (ValueById('205a') <> '') or (ValueById('205b') <> '') then
  F205Exists := true; {b1}

//если присутствуют поля F210a или F210c или F210d  // 210Exists
if (ValueById('210a') <> '') or
   ((ValueById('210c') <> '') and (ValueById('210c') <> 'Б.и.')) or
   (ValueById('210d') <> '') then
     F210Exists := true; {b2}

//если присутствуют поля F215a или F215c или F215d или F215e  // 215Exists
if ValueById('215a') <> '' then
    F215aExists   := true;  //есть F215a  {b3}
if F215aExists or (ValueById('215c') <> '') then
    F215acExists  :=true; //есть F215a или F215c  {b4}
if F215acExists or (ValueById('215d') <> '') then
    F215acdExists :=true; //есть F215a или F215c или F215d {b5}
if F215aExists or (ValueById('215e') <> '') then
    F215aeExists  :=true; {b9}
//if 215acdExists or (ValueById('215d') <> '') then
//    215acdExists := true; //есть F215a или F215c или F215d или F215e    {b6}
if ValueById('225a') <> '' then     // есть 225а
    F225aExists := true; {b7}

//..если присутствуют поля F010a или F010b или F0109  //010Exists
if (ValueById('010a')  <> '') or
   (ValueById('010b') <> '')  or
   (ValueById('0109') <> '')  then
      F010Exists := true; {b8}

//..начинаем формировать запись

   //.. в зависимости от типа товара сведения о кол-ве страниц меняются
   if (ValueById('215a') = 'дискета') or
      (ValueById('215a') = 'CD-ROM')  or
      (ValueById('215a') = 'цифровой диск') then
        ch:='д';
   if (ValueById('215a') = 'аудиокассета') or
      (ValueById('215a') = 'видеокассета') then
        ch:='к';
   if  ValueById('215a') = 'цифровой магнитофон' then
        ch:='м';

   {*---Заглавие---}
    //---Заголовок Б.З.---
  if ValueById('700a') <> '' then // если есть атрибут F700a
      begin
        BR := BR + ValueById('700a');
        if ValueById('700c') <> '' then
          BR := BR + ' ' + ValueById('700c');
        if ValueById('700d') <> '' then
          BR := BR + ' ' + ValueById('700d');
        if ValueById('700b') <> '' then
          BR := BR + ' ' + ValueById('700b');
        if (length(BR) <> 0) and (BR[length(BR)] <> '.') then
          BR := BR + '.';
        Header := AnsiUpperCase(BR) + ' ';
        BR := BR + ' ';
      end;
   //---Основное заглавие---
   if ValueById('200a') <> '' then
     begin
      BR := BR + ValueById('200a');
      Header := Header + ValueById('200a');
      NumOfChar := length(Header)
     end;
   //---Параллельное заглавие---
   if ValueById('200d') <> '' then
     BR := BR + ' ' + '=' + ' ' + ValueById('200d');
   //---Сведения, отн. к заглавию---
   if ValueById('200e') <> '' then
     BR := BR + ':' + ' ' + ValueById('200e');
   //---Первые сведения об ответственности---
   if ValueById('200f') <> '' then
     begin
       exi := true;
       BR  := BR + ' ' + '/ ' + ValueById('200f');
     end;
    //---Послед. сведения об ответственности---
   if ValueById('200g') <> '' then
     begin
       if not exi then
         BR := BR + ' / ' + ValueById('200g')
       else BR := BR + '; ' + ValueById('200g');
     end;
     exi := false;
    //---Обозначение тома---
   if ValueByID('200v') <> '' then
     BR := BR + '. ' + ValueByID('200v');
    //---Номер тома---
   if ValueByID('200h') <> '' then
     BR := BR + ' ' + ValueByID('200h');
    //---Номер тома---
   if ValueByID('200i') <> '' then
     BR := BR + '. ' + ValueByID('200i');

   {---Сведения об издании---}
  if {b1} F205aExists then
    begin
      if (length(BR) <> 0) and (BR[length(BR)] <> '.') then
        BR := BR + '.';
      BR := BR + ' - ';
      if ValueById('205a')<> '' then
        begin
          BR  := BR + ValueById('205a');//основные сведения
          exi := true;
        end;
      if ValueById('205b') <> '' then
         if exi then
          BR := BR + ', ' + ValueById('205b');  //дополнит. сведения
      exi:=false;
     end;
   {---Сведения о выходных данных---}
    if F210Exists then
      begin
        if (length(BR) <> 0) and (BR[length(BR)] <> '.') then
          BR := BR + '.';
        BR := BR + ' - ';

    //---Место издания---
         //заполняем список мест и издателей
         for i := 0 to SourceStringList.Count - 1 do
           begin
             if SourceStringList.Names[i] = '210a' then
               slPlaces.Add(SourceStringList.Values[SourceStringList.Names[i]]);
             if SourceStringList.Names[i] = '210c' then
               slPublishers.Add(SourceStringList.Values[SourceStringList.Names[i]]);
           end;

         {-----}
         i := 0;
         for i := 0 to slPlaces.Count - 1 do
           begin
             if i <> 0 then BR := BR + ', ';
             BR := BR + slPlaces[i];
             if slPublishers.Count - 1 >= i then
             BR := BR + ': ' + slPublishers[i];
           end;
         if slPlaces.Count = 0 then i := 0;

         if slPublishers.Count - 1 >= i then
           for j := i to slPublishers.Count - 1 do
             BR := BR + ', ' + slPublishers[j];
         {-----}
        //---Дата издания---
       if ValueById('210d') <> '' then
         BR := BR + ', ' + ValueById('210d');
      end;
   {-----Количественная характеристика-------}
    if {b6} F215aeExists then
      begin
        if (length(BR) <> 0) and (BR[length(BR)] <> '.') then
          BR := BR + '.';
        BR := BR + ' - ';
        //---Сведения о кол-ве страниц---
       if ValueById('215a') <> '' then
         begin
           BR  := BR + ValueById('215a') + ' ' + ch + '.';
           exi := true;
         end;
        //---Др. уточн-я физ. хар-к---
       if ValueById('215c') <> '' then
         if exi then
           BR := BR + ': ' + ValueById('215c');
       exi:=false;
       //---Размеры---
       if ValueById('215d') <> '' then
         if F215acExists then
           BR := BR + '; ' + ValueById('215d') + ' см.';
       //---Размеры---
       if ValueById('215e') <> '' then
         if F215acdExists then
           BR := BR + ' ' + ValueById('215e') + ' см.';
       end;
     {-----Сведения о серии-------}
     if F225aExists then
       begin
         if (length(BR) <> 0) and (BR[length(BR)] <> '.') then
           BR := BR + '.';
        //---Сведения, отн. к заглавию----
         BR := BR + ' - (' + ValueById('225a');
         if ValueById('225e') <> '' then
           BR := BR + ': ' + ValueById('225e');
        //---Сведения об ответственности----
        if ValueById('225f') <> '' then
          BR := BR + ' / ' + ValueById('225f');
        //---ISSN серии----
        if ValueById('225x') <> '' then
          BR := BR + ', ' + ValueById('225x');
        //---Номер части серии----
        if ValueById('225h') <> '' then
          BR := BR + '; ' + ValueById('225h');
        //---Основное заглавие подсерии---
        if ValueById('225i')  <> '' then
          BR := BR + '. ' + ValueById('225i');
        //---Номер тома серии или подсерии---
        if ValueById('225v') <> '' then
          BR := BR + '; ' + ValueById('225v');
        BR := BR + ')';
       end;
     {-----ISBN--------}
     if F010Exists then
       begin
         if (length(BR) <> 0) and (BR[length(BR)] <> '.') then
           BR := BR + '.';
         BR := BR + ' - ';
        //---Номер ISBN---
        if ValueById('010a') <> '' then
          begin
            BR  := BR + 'ISBN ' + ValueById('010a');
            exi := true;
          end;
        //---Уточнение к ISBN---
        if (ch = 'с') and (ValueById('010b') <> '') then
          begin
            if exi then BR := BR + ' (';
            BR := BR + ValueById('010b');
            if exi then BR := BR + ')';
          end;
        //---Сведения о тираже---
        if ValueById('0109') <> '' then
          begin
            if (ValueById('010b') <> '') or exi then
              BR := BR + ', ';
            BR := BR + ValueById('0109') + ' экз.';
          end;
       end;

 Body := copy(Br,NumOfChar + 1, Length(BR) - NumOfChar);

 FBiblioRecord := BR;      // Полная краткая библиографическая запись
 FBiblioHeader := Header; // заголовок краткой библиографической записи
 FBiblioBody   := Body;   // тело краткой библиографической записи


 result := BR;



end;


procedure TShortBiblioGenerator.PrepareStringList(SourceStringList: TStringList);
var
  st, Value    :string;
  i            :integer;
  PrefixLength :integer;

begin

   PrefixLength := Length(FieldPrefix);

   for i := 0 to SourceStringList.Count - 1 do
     begin

       st := SourceStringList.Names[i];
       Value := Copy(SourceStringList[i], pos('=',SourceStringList[i])+1, 500);
       if FieldPrefix <> '' then
         if copy(st,1,PrefixLength) = FieldPrefix then delete(st,1,PrefixLength);
       AnsiLowerCase(st);
       SourceStringList[i] := st + '=' + Value;

     end;


end;

{ TglRep_Editor }
{
function TShortBiblioGenerator_Editor.GetVerbCount: Integer;
begin
  Result := 1;
end;


function TShortBiblioGenerator_Editor.GetVerb(Index: Integer): string;
begin
  case Index of
    0: Result := 'Execute'; // тестовый вызов генератора
  end;
end;

procedure TShortBiblioGenerator_Editor.ExecuteVerb(Index: Integer);
begin
  case Index of
    0:
    with (Component as TShortBiblioGenerator) do
    begin
     Execute();
     ShowMessage(BiblioRecord);

    end;
  end;
end;
}

end.

Приведенный компонент может быть по Вашему запросу преобразован в компонент ActiveX для использования в любых средах разработки под MS Windows, в.т.ч. VisualBasic, PowerBuilder, 1C etc.

Весь материал, размещенный на сайте www.bookresearch.ru, является собственностью авторов соответствующих материалов. Любая перепечатка и перенос материалов на другие сайты возможны только с разрешения авторов и администратора сайта. Любой может предложить свой материал для публикации у нас. Пишите администратору сайта.

www.bookresearch.ru
Home  : Издателю и книготорговцу : Библиографу : Разработчику : IT-менеджеру : О проекте : Форум : Software - программное обеспечение для книжной отрасли :

  дизайн —
  SiteBuilder.ru


Этот сайт создан при помощи программы Globus SiteBuilder
Этот сайт создан при помощи программы Globus SiteBuilder