TMapTextfile v.99/1

By Hellinger Software.

Class to handle text files as memory mapped files.

Including efficient methodes for access like sequentiell read

or random access read to text, high performance search routines

and many more.

{
  ==============================================================================
  MapTextfiles - Release 99/1  14.03.1999
  for Delphi 4, should also run with Delphi 3

  ------------------------------------------------------------------------------

  MapTextfiles is FREEWARE. Freeware means, that you can use this software
  without paying anything for it, but it is not public domain! This software
  is protected through the law of the Federal Republic of Germany, the European
  Union and other countries.

  (C)1999 by Peter Hellinger Software, All rights are reserved.

  Peter Hellinger Software, Zerzabelshofstrasse 41, D-90480 N黵nberg

  email: [email protected]
  homepage: http://www.helli.de

  ==============================================================================

  Installation:
  Copy MAPTEXTFILE.PAS into your library path. Use ist. 8-)

  ------------------------------------------------------------------------------

  In Delphi you have many ways to manipulate text files. But all of these have
  a handicap: You must read the whole file (StringList) or you can only access
  data sequential (Assign/Readln).

  The Windows API provides the so called Memory Mapped Files. Windows self
  uses MMFs to load EXE or DLL. Therefore the mechanism is very efficient, but
  simple to handle. The only handicap is, that you must know the size of the
  file before you access it. This means for typical text files, that the
  operation is normally limited to read from the file or manipulate inside.

  The class TMapTextfile wraps the neccesary API calls and povides efficent
  functions for accessing the data.

  TMapTextfiles provides the following properties and methods:

  Methodes:
  =========

  Create         Creates an instace of the class

  Destroy        Destroys the instance

  Open           Opens a file as a memory mapped file.

  filename = name of the file
  mode =     open mode:
  mmRead =      Open only for read
  mmReadWrite = Open for read and wrie

  Returns INVALID_HANDLE_VALUE if the file not exist.
  If the result > 0 all is OK.

  NOTE:
  1. The file must exist!
  2. You cannot write behind the end of the file.

  Close          Close the memory mapped file and frees all handles.

  EndOfFile      Returns TRUE, if the End of the file is reached.

  GetSize        Returns the Size of the file in Bytes

  GetPos         Returns the actual file read/write position
  NOTE: Position 0 is the start of the file

  SetPos         Sets the actual read/write position
  NOTE: Position 0 is the start of the file

  ReadChar       Reads a character from the actual read/write position.
  The r/w position is incremented.

  ReadString     Returns a string, starting at the actual r/w position.
  The string is delimited by characters < SPACE, but not
  by ESC (#27) and TAB. The r/w position moves to the
  end of the string, delimiter chararcters are skiped.

  ReadLn         Same as ReadSring, but as a Procedure.

  ReadCharAt     Reads a charater from an arbitray possition.
  The r/w position is NOT moved!

  pos = position to read from (0 = start of the file!)

  ReadChars      Reads a line of charactes from the MMF.
  The r/w position is NOT moved!

  str = The buffer to read to
  pos = position to read from (0 = Start of the file!)
  len = number of characters to read.

  ReadStringAt   Returns a string, starting at an arbitray possition.
  The string is delimited by characters < SPACE, but not
  by ESC (#27) and TAB. The r/w position is NOT moved.

  FindString     Findes a substring in the MMF and Returns the position.

  str = rhe substring to search for
  pos = position to start the search (0 = start of the file)
  max = position to end the search. If this is 0 or less
  then 0 the end of the file is the limit.

  Returns the position of the substring or -1 if the
  substring is not found.

  FindWildCard   Same as Findstring, but supports wildcard search.

  str =   the substring to search for
  pos =   position to start the search (0 = start of the file)
  max =   position to end the search. If this is 0 or less
  then 0 the end of the file is the limit.
  wild =  the character used as wildcard (i.e. "*")
  joker = the character used as joker (i.e. "?")

  Returns the position of the substring or -1 if the
  substring is not found.

  ReadBytes      Reads a number of bytes to a anonymous variable.
  The r/w position is NOT moved!

  b =   the anonymous variable
  pos = position to read from (0 = start of the file)
  len = number of bytes to read.

  WriteBytes     Writes a number of bytes to the file.
  NOTE: You can not write behind the end of the file!!!

  b =   the anonymous variable
  pos = position to write to (0 = start of the file)
  len = number of bytes to write

  ==============================================================================
}

unit uMapTextfile;

interface

uses Classes, Windows;

type
  tMapMode = ( mmRead, mmReadWrite );

type
  TMapTextfile = class
  private
    f_file : THandle;
    f_MMF : THandle;
    f_size : INTEGER;
    f_view : PByte;
    f_data : PChar;
    f_pos : INTEGER;
    f_open : BOOLEAN;
    function CalcPos( pos : INTEGER ) : PChar;
  public
    constructor Create;
    destructor Destroy; override;
    function Open( const filename : string; mode : tMapMode ) : INTEGER;
    procedure Close;
    function ReadChar : CHAR;
    function ReadString : string;
    procedure ReadLn( var str : string );
    function ReadCharAt( pos : LONGINT ) : CHAR;
    procedure ReadChars( str : PChar; pos, len : LONGINT );
    function ReadStringAt( pos : LONGINT ) : string;
    function GetSize : LONGINT;
    function GetPos : LONGINT;
    procedure SetPos( pos : LONGINT );
    function EndOfFile : BOOLEAN;
    function FindString( const str : string; pos, max : INTEGER ) : INTEGER;
    function FindWildCard( const str : string; pos, max : INTEGER;
      wild, joker : CHAR ) : INTEGER;
    procedure ReadBytes( var b; pos, len : LONGINT );
    procedure WriteBytes( var b; pos, len : LONGINT );
  end;

implementation

constructor TMapTextfile.Create;
begin
  f_open := FALSE;
end;

function TMapTextfile.Open( const filename : string; mode : tMapMode )
  : INTEGER;
var
  m1, m2, m3 : CARDINAL;
begin
  f_open := FALSE;
  if mode = mmRead then
  begin
    m1 := GENERIC_READ;
    m2 := PAGE_READONLY;
    m3 := FILE_MAP_READ;
  end else begin
    m1 := GENERIC_READ + GENERIC_WRITE;
    m2 := PAGE_READWRITE;
    m3 := FILE_MAP_WRITE;
  end;

  f_file := CreateFile( PChar( filename ), m1, FILE_SHARE_READ, nil,
    OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, 0 );

  if f_file = INVALID_HANDLE_VALUE then
  begin
    Result := INVALID_HANDLE_VALUE;
    EXIT;
  end;
  try

    f_size := GetFileSize( f_file, nil );

    f_MMF := CreateFileMapping( f_file, nil, m2, 0, f_size, nil );

    if f_MMF = 0 then
    begin
      Result := -1;
      EXIT;
    end;
  finally

    CloseHandle( f_file );
  end;

  try
    f_view := MapViewOfFile( f_MMF, m3, 0, 0, f_size );
    if f_view = nil then
    begin
      Result := -1;
      EXIT;
    end;
  finally
    CloseHandle( f_MMF );
  end;
  f_data := PChar( f_view );
  f_pos := 0;
  f_open := TRUE;
  Result := 0;
end;

destructor TMapTextfile.Destroy;
begin
  if f_open then
    Close;
  inherited;
end;

procedure TMapTextfile.Close;
begin
  if f_open then
  begin
    UnmapViewOfFile( f_view );
    f_open := FALSE;
  end;
end;

function TMapTextfile.CalcPos( pos : INTEGER ) : PChar;
begin
  Result := nil;
  if f_open then
  begin
    if pos < 0 then
      pos := 0;
    if pos > f_size then
      pos := f_size;
    Result := PChar( LONGINT( f_view ) + pos );
  end;
end;

function TMapTextfile.ReadChar : CHAR;
begin
  Result := #0;
  if f_open then
  begin
    f_data := PChar( LONGINT( f_view ) + f_pos );
    Result := f_data^;
    INC( f_pos );
  end;
end;

function TMapTextfile.ReadString : string;
begin
  Result := ‘‘;
  if f_open then
  begin
    f_data := PChar( LONGINT( f_view ) + f_pos );
    while ( f_pos < f_size ) do
    begin
      case f_data^ of
        #0 .. #31 :
          case f_data^ of
            #9, #27 :
              Result := Result + f_data^; // Tab und Escape weiterreichen
            #10 :
              begin
                INC( f_pos );
                EXIT;
              end;
            #13 :
              begin // Carriage Return terminiert
                INC( f_pos );
                INC( f_data );
                if f_data^ = #10 then
                  INC( f_pos );
                EXIT;
              end;
          end;
      else
        Result := Result + f_data^;
      end;
      INC( f_pos );
      INC( f_data );
    end;
  end;
end;

function TMapTextfile.ReadCharAt( pos : LONGINT ) : CHAR;
begin
  if f_open then
    Result := CalcPos( pos )^
  else
    Result := #0;
end;

procedure TMapTextfile.ReadChars( str : PChar; pos, len : LONGINT );
var
  i : INTEGER;
  p : PChar;
begin
  if f_open then
  begin
    if len <= 0 then
      EXIT;
    i := 0;
    p := CalcPos( pos );
    while ( i <= f_size ) and ( i <= len ) do
    begin
      str^ := p^;
      INC( str );
      INC( p );
      INC( i );
    end;
  end;
end;

procedure TMapTextfile.ReadBytes( var b; pos, len : LONGINT );
var
  p : PChar;
begin
  if f_open then
  begin
    p := CalcPos( pos );
    Move( p^, b, len );
  end;
end;

procedure TMapTextfile.WriteBytes( var b; pos, len : LONGINT );
var
  p : PChar;
begin
  if f_open then
  begin
    p := CalcPos( pos );
    Move( b, p^, len );
  end;
end;

function TMapTextfile.ReadStringAt( pos : LONGINT ) : string;
var
  i : INTEGER;
  p : PChar;
begin
  Result := ‘‘;
  if f_open then
  begin
    p := CalcPos( pos );
    i := 0;
    while ( i <= f_size ) do
    begin
      case p^ of
        #0 .. #31 :
          case p^ of
            #9, #27 :
              Result := Result + p^; // Tabs und Escape weiterreichen
            #10, #13 :
              EXIT; // Linefeed and Carriage Return terminiert
          end;
      else
        Result := Result + p^;
      end;
      INC( p );
    end;
  end;
end;

procedure TMapTextfile.ReadLn( var str : string );
begin
  str := ReadString;
end;

function TMapTextfile.GetSize : LONGINT;
begin
  if f_open then
    Result := f_size
  else
    Result := -1;
end;

function TMapTextfile.GetPos : LONGINT;
begin
  if f_open then
    Result := f_pos
  else
    Result := -1;
end;

procedure TMapTextfile.SetPos( pos : LONGINT );
begin
  if f_open then
  begin
    if pos < 0 then
      pos := 0;
    if pos > f_size then
      pos := f_size;
    f_pos := pos;
  end;
end;

function TMapTextfile.EndOfFile : BOOLEAN;
begin
  if f_open then
    Result := f_pos >= f_size
  else
    Result := TRUE;
end;

function TMapTextfile.FindString( const str : string; pos, max : INTEGER )
  : INTEGER;
var
  s, l1, j : INTEGER;
  p, x : PChar;
begin
  Result := -1;
  if f_open then
  begin
    if max <= 0 then
      max := f_size;
    if pos < 0 then
      pos := f_pos;
    if pos > max then
      EXIT;
    x := PChar( str );
    p := PChar( f_view );
    l1 := 0;
    while ( x[ l1 ] > #0 ) do
      INC( l1 );
    if ( l1 > 0 ) then
    begin
      s := pos;
      repeat (* 1 *)
        j := 0;
        while ( s + j < max ) and ( j < l1 ) and ( x[ j ] = p[ s + j ] ) do
        begin
          INC( j );
          if ( j = l1 ) then
          begin
            Result := s;
            EXIT;
          end;
        end;
        INC( s );
      until s >= f_size;
    end;
  end;
end;

function TMapTextfile.FindWildCard( const str : string; pos, max : INTEGER;
  wild, joker : CHAR ) : INTEGER;
var
  s, l1, j : INTEGER;
  p, x : PChar;
begin
  Result := -1;
  if f_open then
  begin
    if max <= 0 then
      max := f_size;
    if pos < 0 then
      pos := f_pos;
    if pos > max then
      EXIT;

    x := PChar( str );
    p := PChar( f_view );
    l1 := 0;
    while ( x[ l1 ] > #0 ) do
      INC( l1 );

    if ( l1 > 0 ) then
    begin
      s := pos;
      repeat (* 1 *)
        j := 0;
        while ( s + j < max ) and ( j < l1 ) and
          ( ( x[ j ] = p[ s + j ] ) or ( x[ j ] = joker ) ) do
        begin
          INC( j );
          if ( x[ j ] = wild ) or ( j >= l1 ) then
          begin
            Result := s;
            EXIT;
          end;
        end;
        INC( s );
      until s >= f_size;
    end;
  end;
end;

end.
时间: 2024-10-19 03:52:54

TMapTextfile v.99/1的相关文章

poj 2762 Going from u to v or from v to u? 【 强连通 拓扑排序】

给出n个点,m条边,问是否任意两点u,v,是否满足u能够到达v,或者v能够到达u 自己写的时候以为缩一下点,然后再判断一下能不能拓扑排序就可以了 但是--wa--- 后来看了这篇题解 http://edward-mj.com/archives/27 按紫书上讲的,如果图中存在有向环,则不存在拓扑排序,反之则存在 所以上面这幅图是满足拓扑排序的 但是因为u,v的入度都为0,u,v之间不能到达 所以缩点完之后的图应该满足是一条长链才行 1 #include<cstdio> 2 #include&l

没结婚那个不费v

http://www.hrm.cn/jobk/%E3%80%87%E9%80%9A%E5%8C%96%E5%93%AA%E9%87%8C%E6%9C%89%E5%8D%96%E5%96%B7%E9%9B%BE%E5%9E%8B%E8%BF%B7%E8%8D%AFQ%EF%BC%9A%EF%BC%96%EF%BC%99%EF%BC%95%EF%BC%92%EF%BC%95%EF%BC%96%EF%BC%97%EF%BC%91%EF%BC%97/ http://www.hrm.cn/jobk/%E2

hdu 4787 GRE Words Revenge 在线AC自动机

hdu 4787 GRE Words Revenge Time Limit: 20000/10000 MS (Java/Others)    Memory Limit: 327680/327680 K (Java/Others)Total Submission(s): 2505    Accepted Submission(s): 614 Problem Description Now Coach Pang is preparing for the Graduate Record Examina

P2456 - 膜拜神犇

P2456 - 膜拜神犇 Description 有一个 n 个点 m 条边的有向图, 蒟蒻可以从 1 号点出发在图上走, 并且最终需要回到 1 号点. 每个点都有一个神犇( 包括 1 号点), 每次经过一个没到过的点, 蒟蒻都会膜拜那位 神犇. 蒟蒻希望膜拜尽可能多的神犇. 由于蒟蒻膜拜神犇的欲望非常强烈, 所以他可以有一次机会逆着一条有向边的方向走. ( 需要注意的是, 这条边的方向不会改变). 你现在想知道, 蒟蒻最多能膜拜多少神犇? Input 第一行 2 个整数 n. m, 分别表示图

货车运输

版权声明:本文为博主原创文章,未经博主允许不得转载. 传送门:货车运输 题目描述 A 国有 n 座城市,编号从 1 到 n,城市之间有 m 条双向道路.每一条道路对车辆都有重量限制,简称限重.现在有 q 辆货车在运输货物, 司机们想知道每辆车在不超过车辆限重的情况下,最多能运多重的货物. 输入输出格式 输入格式: 输入文件名为 truck.in. 输入文件第一行有两个用一个空格隔开的整数 n,m,表示 A 国有 n 座城市和 m 条道 路. 接下来 m 行每行 3 个整数 x. y. z,每两个

UVa 1449 Dominating Patterns

方法:AC自动机 题意比较明显,用ac 自动机.陷阱是可能会出现重复的string. code: 1 #include <cstdio> 2 #include <cstring> 3 #include <algorithm> 4 #include <iostream> 5 #include <string> 6 #include <vector> 7 #include <stack> 8 #include <bits

BZOJ 1036: [ZJOI2008]树的统计Count (树链剖分模板题)

1036: [ZJOI2008]树的统计Count Time Limit: 10 Sec  Memory Limit: 162 MBSubmit: 14982  Solved: 6081[Submit][Status][Discuss] Description 一棵树上有n个节点,编号分别为1到n,每个节点都有一个权值w.我们将以下面的形式来要求你对这棵树完成一些操作: I. CHANGE u t : 把结点u的权值改为t II. QMAX u v: 询问从点u到点v的路径上的节点的最大权值 I

Countries

Countries 题目链接:http://hihocoder.com/problemset/problem/1391 预处理+双指针 首先将A->B,B->A的导弹全部转化为B->A的导弹(因为不需要计算B承受的伤害,所以对于A->B的导弹,只需记录被B的防护罩返回来的导弹即可). 然后对于每个导弹计算将其反弹回B,A所需要的最小的防护罩区间[l,r](这个操作在O(1)的时间完成,画张图就很好推了) 于是问题就转化为了: 数轴上有一些固定区间,每个固定区间都有一个权值,现在有一

安卓端与开发板通信

安卓端与开发板通信 1.由于我们本实验使用到的是串口2,,即串口2给wifi核心板使用,改变跳线帽,让原来串口2是提供给zigbee使用的,改为给wifi使用. 2.添加ser2net应用程序 上一次我们成功的让驱动程序支持了串口 2,并且做了简单的测试.接下来, 我们就为串口 2 添加一个应用程序,从而实现 Wi-Fi 串口 # cd /openwrt/trunk/ # make menuconfig Network -> ser2net 保存退出 # make V=99 3.烧录固件,进入系