4

私は Delphi 2007 (Unicode サポートなし) で作業しており、Google Analytics API から XML および JSON データを取得しています。以下は、URL 紹介パス用に取得した UTF-8 でエンコードされたデータの一部です。

ga:referralPath=/add/%D0%9F%D0%B8%D0%B6%D0%B0%D0%BC

このデコーダーを使用してデコードすると、これが適切に生成されます。

ga:referralPath=/add/詳細

このデコードを実行する Delphi 2007 で使用できる関数はありますか?

UPDATE このデータは URL に対応しています。最終的に私がやりたいことは、これを SqlServer データベースに保存することです (箱から出して-文字セットに関する設定は変更されていません)。そして、このページへの有効なリンクを含む html ページを生成/作成できるようになります (注: この例では、URL 参照パスのみを扱っています。有効な URL リンクを作成するには、ソースが必要になることは明らかです)。

4

2 に答える 2

6

D2007 は Unicode をサポートしていますが、D2009+ ほどではありません。D2007 の Unicode は、WideString存在する少数の RTL サポート関数を使用して処理されます。

URL には、パーセントでエンコードされた UTF-8 バイト オクテットが含まれています。これらのシーケンスをバイナリ表現に変換し、 を使用UTF8Decode()して UTF-8 データをWideString. 例えば:

function HexToBits(C: Char): Byte;
begin
  case C of
    '0'..'9': Result := Byte(Ord(C) - Ord('0'));
    'a'..'f': Result := Byte(10 + (Ord(C) - Ord('a')));
    'A'..'F': Result := Byte(10 + (Ord(C) - Ord('A')));
  else
    raise Exception.Create('Invalid encoding detected');
  end;
end;

var
  sURL: String;
  sWork: UTF8String;
  C: Char;
  B: Byte;
  wDecoded: WideString;
  I: Integer;
begin
  sURL := 'ga:referralPath=/add/%D0%9F%D0%B8%D0%B6%D0%B0%D0%BC';
  sWork := sURL;
  I := 1;
  while I <= Length(sWork) do
  begin
    if sWork[I] = '%' then
    begin
      if (I+2) > Length(sWork) then
        raise Exception.Create('Incomplete encoding detected');
      sWork[I] := Char((HexToBits(sWork[I+1]) shl 4) or HexToBits(sWork[I+2]));
      Delete(sWork, I+1, 2);
    end;
    Inc(I);
  end;
  wDecoded := UTF8Decode(sWork);
  ...
end;
于 2013-01-01T06:54:29.530 に答える
1

Windows API を使用する次のコードを使用できます。

function Utf8ToStr(const Source : string) : string;
var
  i, len : integer;
  TmpBuf : array of byte;
begin
  SetLength(Result, 0);
  i := MultiByteToWideChar(CP_UTF8, 0, @Source[1], Length(Source), nil, 0);
  if i = 0 then Exit;
  SetLength(TmpBuf, i * SizeOf(WCHAR));
  Len := MultiByteToWideChar(CP_UTF8, 0, @Source[1], Length(Source), @TmpBuf[0], i);
  if Len = 0 then Exit;

  i := WideCharToMultiByte(CP_ACP, 0, @TmpBuf[0], Len, nil, 0, nil, nil);
  if i = 0 then Exit;

  SetLength(Result, i);
  i := WideCharToMultiByte(CP_ACP, 0, @TmpBuf[0], Len, @Result[1], i, nil, nil);
  SetLength(Result, i);
end;
于 2013-01-01T09:19:27.850 に答える