Автор: de1phi | 18.12.2007 в 10:22 | Рубрики: ASCII

В файле asciidrv.txt насчет последнего числа в строке схемы поля говорится:

“* Offset - Number of characters from the beginning of the line that the field begins. Used for FIXED format only.” (Offset - количество символов он начала линии до начала поля. Используется только для фиксированного формата.).

С тех пор, как мой файл имеет переменный (Variable) формат, я задал в каждой строке смещение, равное нулю. После некоторых попыток, чтобы заставить это работать, я следал следующие изменения:

[discs]
filetype = varying
charset = ascii
delimiter = ”
separator = ,
field1 = id,char,10,0,1
field2 = title,char,30,0,2
field3 = artist,char,30,0,3

field36 = song30,char,50,0,36

После более произвольных изменений это стало таким:

[discs]
filetype = varying
charset = ascii
delimiter = ”
separator = ,
field1 = id,char,10,0,10
field2 = title,char,30,0,20
field3 = artist,char,30,0,30

field36 = song30,char,50,0,360

и внезапно все заработало! Для поля, которое игнорируется форматом файла, “Offset” несомненно дало огромный эффект.

Автор: de1phi | в 10:22 | Рубрики: ASCII

unit Cdbascii;

interface

uses
SysUtils, WinTypes, WinProcs, Messages, Classes, Graphics, Controls,
Forms, Dialogs, DbiErrs, DbiTypes, DbiProcs, DB, DBTables;

type
TAsciiDelimTable = class(TTable)
private
{ Private declarations }
fQuote: Char;
fDelim: Char;
protected
{ Protected declarations }
function CreateHandle: HDBICur; override;
procedure SetQuote(newValue: Char);
procedure SetDelim(newValue: Char);
public
{ Public declarations }
constructor Create(AOwner: TComponent); override;
destructor Destroy; override;
{ Эти свойства не должны больше публиковаться }
property IndexFieldNames;
property IndexName;
property MasterFields;
property MasterSource;
property UpdateMode;
published
{ Published declarations }
property Quote: Char read fQuote write setQuote default ‘”‘;
property Delim: Char read fDelim write setDelim default ‘,’;
end;

procedure Register;

implementation

uses DBConsts;

procedure Register;
begin
RegisterComponents(’Data Access’, [TAsciiDelimTable]);
end;

constructor TAsciiDelimTable.Create(AOwner: TComponent);
begin
inherited Create(AOwner);
Exclusive := True;
TableType := ttASCII;
fQuote := ‘”‘;
fDelim := ‘,’;
end;

destructor TAsciiDelimTable.Destroy;
begin
inherited Destroy;
end;

{ Рабочий код }

function CheckOpen(Status: DBIResult): Boolean;
begin
case Status of
DBIERR_NONE:
Result := True;
DBIERR_NOTSUFFTABLERIGHTS:
begin
if not Session.GetPassword then
DbiError(Status);
Result := False;
end;
else
DbiError(Status);
end;
end;

function TAsciiDelimTable.CreateHandle: HDBICur;
const
OpenModes: array[Boolean] of DbiOpenMode = (dbiReadWrite, dbiReadOnly);
ShareModes: array[Boolean] of DbiShareMode = (dbiOpenShared, dbiOpenExcl);
var
STableName: array[0..SizeOf(TFileName) - 1] of Char;
SDriverType: array[0..12] of Char;
begin
if TableName = ” then
DBError(SNoTableName);
AnsiToNative(DBLocale, TableName, STableName, SizeOf(STableName) - 1);
StrPCopy(SDriverType, ‘ASCIIDRV-’ + Quote + ‘-’ + Delim);
Result := nil;
while not CheckOpen(DbiOpenTable(DBHandle, STableName, SDriverType,
nil, nil, 0, OpenModes[ReadOnly], ShareModes[Exclusive],
xltField, False, nil, Result)) do {Повтор}
;
end;

procedure TAsciiDelimTable.SetQuote(newValue: Char);
begin
if Active then
{ DBError(SInvalidBatchMove); };
fQuote := newValue;
end;

procedure TAsciiDelimTable.SetDelim(newValue: Char);
begin
if Active then
{ DBError(SInvalidBatchMove); };
fDelim := newValue;
end;

end.

Автор: de1phi | в 10:22 | Рубрики: ASCII

Hа боpту самолета:
- Здpавствуйте, дамы и господа, - говоpит командиp экипажа. - Мы благодаpим вас за то, что вы выбpали нашу авиакомпанию для пеpвого полета в пеpвый день нового 2000 года. Мы находимся на высоте 3 тыс. футов, наша скоpость… вау!… ох, блин!… вот фак!… Извините за неудобства, котоpые вы испытываете, находясь вниз головой, надеюсь, все были пpистегнуты. Есть ли сpеди пассажиpов на боpту пpогpаммист?

Классы Tstrings/TStringlist имеют свойство commatext, которое автоматически разделяет строки, содержащие разделители, на отдельные части. Пример показывает как считать CSV файл. В Конечном итоге, автоматически разделённые строки содержатся в TStringlist.

var
ts: tstringlist;
S: string;
Tf: Textfile;
begin
Ts := Tstringlist.create;
Assignfile(tf, ‘filename’);
Reset(tf);
while not eof(tf) do
begin
Readln(tf,S);
Ts.CommaText := S;
//ProcessLine;
end;
closefile(tf);
ts.free;
end;

Так же операцию можно производить в обратном порядке.

Свойство Commatext поддерживает разделители как в виде запятых, так и двойных кавычек: 1,2,3,4 и “1″,”2″,”3″,”4″

Например, строка вида “1″,”2,3″,”4″ будет разделена на три элемента, которые заключены в кавычки (средняя запятая будет проигнорирована). Чтобы включить кавычку в конечный результ, нужно поставить две кавычки подряд: “1″,”"2″ (результат будет 1 и “2 ).

unit Unit1;

interface

uses
Windows, Messages, SysUtils, Classes, Graphics, Controls,
Forms, Dialogs, StdCtrls, Db, DBTables, Grids, DBGrids;

type
TForm1 = class(TForm)
DBGrid1: TDBGrid;
MyTable: TTable;
DataSource1: TDataSource;
Button1: TButton;
procedure Button1Click(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
procedure ExportToASCII;
end;
Читать полностью…

function ConvertTo852(S: string): string;
var
A : integer;
Ch : char;
begin
setlength(Result,Length(S));
for A := 1 to length(S) do
begin
case S[A] of
: Ch := <852code>
: Ch := <852code2>

else Ch := S[A];
end;
Result[A] := Ch;
end;
end;