procedure TForm1.Button1Click(Sender: TObject);
var s:string;
begin
  s:='abcdefg';
  edit1.Text := s[1];
end;
  当edit1.Text := s[1];的时候 edit1.text是a
  edit1.Text := s[0];编译出错:Element 0 inaccessible - use 'Length' or 'SetLength'  s[0];存放着什么东西??
  还有不是说delphi里的字符串  开头4个字节是引用记数  第2字节才是字符Length吗?这里怎么是这样子的呢??
  当当edit1.Text := s[9];的时候  编译运行却不会出错 edit1.Text := s[345]; 也可以通过
不是说string类型默认是255个字符?  怎么能用到345上去呢??
  

解决方案 »

  1.   

    首先要讲的是S[0]确实是存放字串的长度,所以你这句"edit1.Text := s[0];编译出错:Element 0 inaccessible - use 'Length' or 'SetLength'"错误是很正常的.
      

  2.   

    至于为什么像s[9]为什么编译不会出错,我想可能是Delphi的String类型不是以"\0"结尾的,而且它是动态分配空间的,所以上面你的s[9]就是一个随机字符.s[345]我也不知道为什么会这样,理论上应该是不对的
      

  3.   

    Delphi中的String类型默认的是AnsiString, 而不是ShortString,除非你使用 {$H-} 进行编译。ShortString才是标准Pascal的String, 最多存放255个字符,其中[0]处为长度,字符是从[1]处开始存放的。AnsiString最多可以存放2^31个字符,字符是从[1]处开始存放,但是[0]处已经不再是长度了(原因很简单,一个字节并不能存放下AnsiString的长度值了)。因此:这段代码是能正常运行的。
    var
      S : ShortString;
      I : Integer;
    begin
      S := '1234567890';
      I := Ord(S[0]);
    end;
    面这段代码是无法编译的,编译时会报错“Element 0 inaccessible - use 'Length' or 'SetLength'”。
    var
      S : AnsiString;
      I : Integer;
    begin
      S := '1234567890';
      I := Ord(S[0]);
    end;
      

  4.   

    不是说string类型默认是255个字符?  怎么能用到345上去呢??
    ---------------------------------------------------------
    不同的編譯開關下String類型不同的(ShortString ,AnsiString),通常情況下是
    AnsiString,因此長度不止255個字符.//DelphiX Developer's Guide 有介紹
      

  5.   

    http://community.csdn.net/Expert/topic/4105/4105014.xml?temp=.8780481
      

  6.   

    现在要是AnsiString类型的字符串变量的第一个字节不是存放串length的话  那为什么还要保留这一个字节?  还有要是不是以"\0"结尾的   那编译器怎么判断串有多大?
      

  7.   

    =====================================================================================
    现在要是AnsiString类型的字符串变量的第一个字节不是存放串length的话  那为什么还要保留这一个字节?  还有要是不是以"\0"结尾的   那编译器怎么判断串有多大?
    =====================================================================================1. AnsiString已经不能使用[0]来获得长度。
    2. AnsiString的长度仍然在头部,这个头部已经不是一个字节了。
    3. AnsiString还是PASCAL字符串,而不是以"\0"结尾的C字符串。
      

  8.   

    AnsiString的长度仍然在头部,这个头部已经不是一个字节了。
    ---------------------------------
    ???
    procedure TForm1.Button1Click(Sender: TObject);
    var s:string;
    begin
      s:='abcdefg';
      edit1.Text := s[1];
    end;
      当edit1.Text := s[1];的时候 edit1.text是a  比s[1]更前面的“头部”应该就是s[0]了吧   可是s[0]也就一个字节啊  难道s[0]前面还有东西???****************************
    正如图2 - 1演示的,A n s i S t r i n g字符串类型有引用计数的功能,这表示几个字符串都能指向相同的物理地址。因此,复制字符串因为仅仅是复制了指针而不是复制实际的字符串而变得非常快。这个是从delphi5开发人员指南里copy过来的  图2的内容是ansiString的内存分布:
    头4个字节是"分配大小" ,接下来是"引用记数" ,再下来是"长度" ,"长度"后面好象还有一个字节空着不用 ,接着才是存放字符的空间  最后面的一个字节是#0   
    这样的话:s[0]代表什么东西呢?  在s[0]前面是不是应该还有其他东西?? 
    既然最后面一个字节是#0  那为什么   edit1.Text := s[345]; 这样的已经严重超出串大小却不会出错???
      

  9.   

    上面不是已经告诉楼往:AnsiString不能引用[0]这个元素。也就是说,s[0]根本不能用,所以s[0]不代表任何东西。楼主自己也已经查到Delphi的文档了:这个是从delphi5开发人员指南里copy过来的  图2的内容是ansiString的内存分布:
    头4个字节是"分配大小" ,接下来是"引用记数" ,再下来是"长度" ,"长度"后面好象还有一个字节空着不用 ,接着才是存放字符的空间  最后面的一个字节是#0   很显然,AnsiStirng的头部已经不是一个字节了,从上面的文档来看,应该至少有13个字节,可能更多,没有仔细研究过这个头部。正在由于AnsiString的头部变得比ShortString复杂得多,所以这个头部内容的维护应该交给Delphi来完成,Delphi没有象ShortString那样提供AnsiString的s[0]这种引用方法了。不管是ShortString还是AnsiString或者WideString,都可以引用s[1],...s[i],而s[0]只有ShortString才能引用,对AnsiString和WideString的s[0]引用都通不过编译的。