Ignore:
Timestamp:
Jun 12, 2007, 7:24:38 PM (17 years ago)
Author:
イグトランス (egtra)
Message:

StringBuilderを追加。String不変へ。共通の文字列操作関数をActiveBasic.Strings内に配置(設計に検討の余地あり)。

File:
1 edited

Legend:

Unmodified
Added
Removed
  • Include/Classes/System/String.ab

    r270 r272  
    22
    33#require <basic/function.sbp>
     4#require <Classes/System/Text/StringBuilder.ab>
     5#require <Classes/ActiveBasic/Strings/Strings.ab>
    46
    57#ifdef __STRING_IS_NOT_ALWAYS_UNICODE
     
    2123
    2224        m_Length As Long
     25        Chars As *StrChar
     26
     27        Sub validPointerCheck(p As VoidPtr, size = 1 As Long)
     28            If p As ULONG_PTR < &h10000 Then
     29                'Throw ArgumentException
     30                Debug
     31            ElseIf IsBadReadPtr(p, size As ULONG_PTR) Then
     32                'Throw ArgumentException
     33                Debug
     34            End If
     35        End Sub
    2336    Public
    24         Chars As *StrChar
     37        Static Const Empty = New String
    2538
    2639        Sub String()
    27             Chars = _System_malloc(SizeOf (StrChar))
    28             Chars[0] = 0
    29             m_Length = 0
     40'           Chars = 0
     41'           m_Length = 0
     42        End Sub
     43
     44        Sub String(initStr As PCWSTR)
     45            validPointerCheck(initStr)
     46            Assign(initStr, lstrlenW(initStr))
     47        End Sub
     48
     49        Sub String(initStr As PCWSTR, length As Long)
     50            validPointerCheck(initStr, length)
     51            Assign(initStr, length)
     52        End Sub
     53
     54        Sub String(initStr As PCWSTR, start As Long, length As Long)
     55            If start < 0 Or length Or start + length < 0 Then
     56                'Throw New ArgumentOutOfRangeException
     57            End If
     58            validPointerCheck(initStr + start, length)
     59            Assign(initStr + start, length)
    3060        End Sub
    3161
    3262        Sub String(initStr As PCSTR)
    33             Assign(initStr)
     63            validPointerCheck(initStr)
     64            Assign(initStr, lstrlenA(initStr))
    3465        End Sub
    3566
    3667        Sub String(initStr As PCSTR, length As Long)
     68            validPointerCheck(initStr, length)
    3769            Assign(initStr, length)
    3870        End Sub
    3971
    40         Sub String(initStr As PCWSTR)
    41             Assign(initStr)
    42         End Sub
    43 
    44         Sub String(initStr As PCWSTR, length As Long)
    45             Assign(initStr, length)
    46         End Sub
    47 
    48         Sub String(ByRef initStr As String)
    49             Assign(initStr)
    50         End Sub
    51 
    52         Sub String(length As Long)
    53             ReSize(length)
     72        Sub String(initStr As PCSTR, start As Long, length As Long)
     73            If start < 0 Or length Or start + length < 0 Then
     74                'Throw New ArgumentOutOfRangeException
     75            End If
     76            validPointerCheck(initStr + start, length)
     77            Assign(initStr + start, length)
     78        End Sub
     79       
     80        Sub String(initStr As String)
     81            If Not String.IsNullOrEmpty(initStr) Then
     82                Assign(initStr.Chars, initStr.m_Length)
     83            End If
    5484        End Sub
    5585
    5686        Sub String(initChar As StrChar, length As Long)
    57             ReSize(length, initChar)
    58         End Sub
    59 
    60         Sub ~String()
    61             _System_free(Chars)
    62             Chars = 0
    63 #ifdef _DEBUG
    64             m_Length = 0
    65 #endif
     87            AllocStringBuffer(length)
     88            ActiveBasic.Strings.ChrFill(Chars, length, initChar)
     89            Chars[length] = 0
     90        End Sub
     91
     92        Sub String(sb As System.Text.StringBuilder)
     93            Chars = StrPtr(sb)
     94            m_Length = sb.Length
     95            sb.__Stringized()
    6696        End Sub
    6797
     
    75105
    76106        Const Function Operator [] (n As Long) As StrChar
    77 #ifdef _DEBUG
    78             If n > Length Then
    79                 'Throw ArgumentOutOfRangeException
    80                 Debug
    81             End If
    82 #endif
     107            rangeCheck(n)
    83108            Return Chars[n]
    84109        End Function
    85110
    86         Sub Operator []= (n As Long, c As StrChar)
    87 #ifdef _DEBUG
    88             If n >= Length Then
    89                 'Throw ArgumentOutOfRangeException
    90                 Debug
    91             End If
    92 #endif
    93             Chars[n] = c
    94         End Sub
    95 
    96     /*  Const Function Operator + (text As *Byte) As String
    97             Return Concat(text As PCTSTR, lstrlen(text))
    98         End Function*/
    99 
    100         Const Function Operator + (text As PCSTR) As String
    101             Return Concat(text, lstrlenA(text))
    102         End Function
    103 
    104         Const Function Operator + (text As PCWSTR) As String
    105             Return Concat(text, lstrlenW(text))
    106         End Function
    107 
    108         Const Function Operator + (objString As String) As String
    109             Return Concat(objString.Chars, objString.m_Length)
    110         End Function
    111 
    112         Const Function Operator & (text As PCSTR) As String
    113             Dim tempString = This + text
     111        Const Function Operator + (y As PCSTR) As String
     112            Return Concat(y, lstrlenA(y))
     113        End Function
     114
     115        Const Function Operator + (y As PCWSTR) As String
     116            Return Concat(y, lstrlenW(y))
     117        End Function
     118
     119        Const Function Operator + (y As String) As String
     120            Return Concat(y.Chars, y.m_Length)
     121        End Function
     122
     123        Const Function Operator & (y As PCSTR) As String
     124            Return This + y
     125        End Function
     126
     127        Const Function Operator & (y As PCWSTR) As String
     128            Dim tempString = This + y
    114129            Return tempString
    115130        End Function
    116131
    117         Const Function Operator & (text As PCWSTR) As String
    118             Dim tempString = This + text
     132        Const Function Operator & (y As String) As String
     133            Dim tempString = This + y
    119134            Return tempString
    120135        End Function
    121136
    122         Const Function Operator & (objString As String) As String
    123             Dim tempString = This + objString
    124             Return tempString
    125         End Function
    126 
    127         Const Function Operator == (objString As String) As Boolean
    128             Return String.Compare(This, objString) = 0
    129         End Function
    130 
    131         Const Function Operator == (text As *StrChar) As Boolean
    132             Return _System_StrCmp(This.Chars, text) = 0
    133         End Function
    134 
    135         Const Function Operator <> (objString As String) As Boolean
    136             Return String.Compare(This, objString) <> 0
    137         End Function
    138 
    139         Const Function Operator <> (text As *StrChar) As Boolean
    140             Return _System_StrCmp(This.Chars, text) <> 0
    141         End Function
    142 
    143         Const Function Operator < (objString As String) As Boolean
    144             Return String.Compare(This, objString) < 0
    145         End Function
    146 
    147         Const Function Operator < (text As *StrChar) As Boolean
    148             Return _System_StrCmp(This.Chars, text) < 0
    149         End Function
    150 
    151         Const Function Operator > (objString As String) As Boolean
    152             Return String.Compare(This, objString) > 0
    153         End Function
    154 
    155         Const Function Operator > (text As *StrChar) As Boolean
    156             Return _System_StrCmp(This.Chars, text) > 0
    157         End Function
    158 
    159         Const Function Operator <= (objString As String) As Boolean
    160             Return String.Compare(This, objString) <= 0
    161         End Function
    162 
    163         Const Function Operator <= (text As *StrChar) As Boolean
    164             Return _System_StrCmp(This.Chars, text) <= 0
    165         End Function
    166 
    167         Const Function Operator >= (objString As String) As Boolean
    168             Return String.Compare(This, objString) >= 0
    169         End Function
    170 
    171         Const Function Operator >= (text As *StrChar) As Boolean
    172             Return _System_StrCmp(This.Chars, text) >= 0
     137        Const Function Operator == (y As String) As Boolean
     138            Return String.Compare(This, y) = 0
     139        End Function
     140
     141        Const Function Operator == (y As *StrChar) As Boolean
     142            Return String.Compare(This, y) = 0
     143        End Function
     144
     145        Const Function Operator <> (y As String) As Boolean
     146            Return String.Compare(This, y) <> 0
     147        End Function
     148
     149        Const Function Operator <> (y As *StrChar) As Boolean
     150            Return String.Compare(This, y) <> 0
     151        End Function
     152
     153        Const Function Operator < (y As String) As Boolean
     154            Return String.Compare(This, y) < 0
     155        End Function
     156
     157        Const Function Operator < (y As *StrChar) As Boolean
     158            Return String.Compare(This, y) < 0
     159        End Function
     160
     161        Const Function Operator > (y As String) As Boolean
     162            Return String.Compare(This, y) > 0
     163        End Function
     164
     165        Const Function Operator > (y As *StrChar) As Boolean
     166            Return String.Compare(This, y) > 0
     167        End Function
     168
     169        Const Function Operator <= (y As String) As Boolean
     170            Return String.Compare(This, y) <= 0
     171        End Function
     172
     173        Const Function Operator <= (y As *StrChar) As Boolean
     174            Return String.Compare(This, y) <= 0
     175        End Function
     176
     177        Const Function Operator >= (y As String) As Boolean
     178            Return String.Compare(This, y) >= 0
     179        End Function
     180
     181        Const Function Operator >= (y As *StrChar) As Boolean
     182            Return String.Compare(This, y) >= 0
    173183        End Function
    174184
     
    177187        End Function
    178188
     189    Public
    179190        Static Function Compare(x As String, indexX As Long, y As String, indexY As Long, length As Long) As Long
    180             Return CompareOrdinal(x, indexX, y, indexY, length)
     191            Return String.CompareOrdinal(x, indexX, y, indexY, length)
    181192        End Function
    182193
    183194        Static Function CompareOrdinal(x As String, y As String) As Long
    184             Return _System_StrCmp(x.Chars, y.Chars)
     195            Return String.CompareOrdinal(x.Chars, y.Chars)
    185196        End Function
    186197
    187198        Static Function CompareOrdinal(x As String, indexX As Long, y As String, indexY As Long, length As Long) As Long
    188             If Object.ReferenceEquals(x, Nothing) Then
    189                 If Object.ReferenceEquals(y, Nothing) Then
     199            Return String.CompareOrdinal(x.Chars, indexX, y.Chars, indexY, length)
     200        End Function
     201    Private
     202        Static Function Compare(x As String, y As *StrChar) As Long
     203            Return String.CompareOrdinal(x, y)
     204        End Function
     205
     206        Static Function CompareOrdinal(x As String, y As *StrChar) As Long
     207            Return String.CompareOrdinal(x.Chars, y)
     208        End Function
     209
     210        Static Function CompareOrdinal(x As *StrChar, y As *StrChar) As Long
     211            If x = 0 Then
     212                If y = 0 Then
    190213                    Return 0
    191214                Else
    192215                    Return -1
    193216                End If
    194             ElseIf Object.ReferenceEquals(y, Nothing) Then
     217            ElseIf y = 0 Then
    195218                Return 1
    196219            End If
    197             Return _System_StrCmpN(VarPtr(x.Chars[indexX]), VarPtr(y.Chars[indexY]), length As SIZE_T)
    198         End Function
    199 
     220            Return ActiveBasic.Strings.StrCmp(x, y)
     221        End Function
     222
     223        Static Function CompareOrdinal(x As *StrChar, indexX As Long, y As *StrChar, indexY As Long, length As Long) As Long
     224            If x = 0 Then
     225                If y = 0 Then
     226                    Return 0
     227                Else
     228                    Return -1
     229                End If
     230            ElseIf y = 0 Then
     231                Return 1
     232            End If
     233            Return ActiveBasic.Strings.ChrCmp(VarPtr(x[indexX]), VarPtr(y[indexY]), length As SIZE_T)
     234        End Function
     235    Public
    200236        Function CompareTo(y As String) As Long
    201237            Return String.Compare(This, y)
     
    207243    '           Throw New ArgumentException
    208244    '       End If
    209             Return CompareTo(y)
     245            Return CompareTo(y As String)
    210246        End Function
    211247
     
    213249            Return Chars
    214250        End Function
    215 
    216         Sub ReSize(allocLength As Long)
    217             If allocLength < 0 Then Exit Sub
    218             Dim oldLength  = m_Length
    219             If AllocStringBuffer(allocLength) <> 0 Then
    220                 If allocLength > oldLength Then
    221                     ZeroMemory(VarPtr(Chars[oldLength]), SizeOf (StrChar) * (m_Length - oldLength + 1))
    222                 Else
    223                     Chars[m_Length] = 0
    224                 End If
    225             End If
    226         End Sub
    227 
    228         Sub ReSize(allocLength As Long, c As StrChar)
    229             If allocLength < 0 Then Exit Sub
    230             Dim oldLength = m_Length
    231             If AllocStringBuffer(allocLength) <> 0 Then
    232                 If allocLength > oldLength Then
    233                     _System_FillChar(VarPtr(Chars[oldLength]), (m_Length - oldLength) As SIZE_T, c)
    234                 End If
    235                 Chars[m_Length] = 0
    236             End If
    237         End Sub
     251Private
    238252
    239253        Sub Assign(text As PCSTR, textLengthA As Long)
     
    261275        End Sub
    262276
    263         Sub Assign(ByRef objString As String)
    264             Assign(objString.Chars, objString.m_Length)
    265         End Sub
    266 
    267         Sub Assign(text As PCSTR)
    268             If text Then
    269                 Assign(text, lstrlenA(text))
    270             Else
    271                 If Chars <> 0 Then
    272                     Chars[0] = 0
    273                 End If
    274                 m_Length = 0
    275             End If
    276         End Sub
    277 
    278         Sub Assign(text As PCWSTR)
    279             If text Then
    280                 Assign(text, lstrlenW(text))
    281             Else
    282                 If Chars <> 0 Then
    283                     Chars[0] = 0
    284                 End If
    285                 m_Length = 0
    286             End If
    287         End Sub
    288 
    289         Sub Append(text As *StrChar, textLength As Long)
    290             Dim prevLen As Long
    291             prevLen = m_Length
    292             If AllocStringBuffer(m_Length + textLength) <> 0 Then
    293                 memcpy(VarPtr(Chars[prevLen]), text, SizeOf (StrChar) * textLength)
    294                 Chars[m_Length] = 0
    295             End If
    296         End Sub
    297 
    298         Sub Append(text As *StrChar)
    299             Append(text, lstrlen(text))
    300         End Sub
    301 
    302         Sub Append(ByRef str As String)
    303             Append(str.Chars, str.m_Length)
    304         End Sub
    305 
    306         Const Function Clone() As String
    307             Return This
    308         End Function
    309277    Private
    310278        Static Function ConcatStrChar(text1 As *StrChar, text1Length As Long, text2 As *StrChar, text2Length As Long) As String
     
    312280            With ConcatStrChar
    313281                .AllocStringBuffer(text1Length + text2Length)
    314                 memcpy(.Chars, text1, SizeOf (StrChar) * text1Length)
    315                 memcpy(VarPtr(.Chars[text1Length]), text2, SizeOf (StrChar) * text2Length)
     282                ActiveBasic.Strings.ChrCopy(.Chars, text1, text1Length As SIZE_T)
     283                ActiveBasic.Strings.ChrCopy(VarPtr(.Chars[text1Length]), text2, text2Length As SIZE_T)
    316284                .Chars[text1Length + text2Length] = 0
    317285            End With
     
    324292            With Concat
    325293                Dim lenW = MultiByteToWideChar(CP_THREAD_ACP, 0, text, len, 0, 0)
     294                Concat = New String
    326295                .AllocStringBuffer(m_Length + lenW)
    327                 memcpy(.Chars, This.Chars, m_Length)
     296                ActiveBasic.Strings.ChrCopy(.Chars, This.Chars, m_Length)
    328297                MultiByteToWideChar(CP_THREAD_ACP, 0, text, len, VarPtr(.Chars[m_Length]), lenW)
    329298                .Chars[m_Length + lenW] = 0
     
    335304#ifdef __STRING_IS_NOT_UNICODE
    336305            With Concat
     306                Concat = New String
    337307                Dim lenA = WideCharToMultiByte(CP_THREAD_ACP, 0, text, len, 0, 0, 0, 0)
    338308                .AllocStringBuffer(m_Length + lenA)
    339                 memcpy(.Chars, This.Chars, m_Length)
     309                ActiveBasic.Strings.ChrCopy(.Chars, This.Chars, m_Length As SIZE_T)
    340310                WideCharToMultiByte(CP_THREAD_ACP, 0, text, len, VarPtr(.Chars[m_Length]), lenA, 0, 0)
    341311                .Chars[m_Length + lenA] = 0
     
    358328        End Function
    359329
    360         Const Function Contains(objString As String) As Boolean
    361             Return IndexOf(objString, 0, m_Length) >= 0
    362         End Function
    363 
    364         Const Function Contains(lpszText As *StrChar) As Boolean
    365             Return IndexOf(lpszText, 0, m_Length) >= 0
    366         End Function
    367 
    368         Const Function IndexOf(lpszText As *StrChar) As Long
    369             Return IndexOf(lpszText, 0, m_Length)
    370         End Function
    371 
    372         Const Function IndexOf(lpszText As *StrChar, startIndex As Long) As Long
    373             Return IndexOf(lpszText, startIndex, m_Length - startIndex)
    374         End Function
    375 
    376         Const Function IndexOf(lpszText As *StrChar, startIndex As Long, count As Long) As Long
    377             Dim length = lstrlen(lpszText)
    378 
    379             If startIndex < 0 Then Return -1
    380             If count < 1 Or count + startIndex > m_Length Then Return -1
    381             If length > m_Length Then Return -1
    382 
     330        Const Function Contains(s As String) As Boolean
     331            If Object.ReferenceEquals(s, Nothing) Then
     332                'Throw New ArgumentNullException
     333            End If
     334            Return IndexOf(s, 0, m_Length) >= 0
     335        End Function
     336
     337        Const Function IndexOf(c As StrChar) As Long
     338            Return indexOfCore(c, 0, m_Length)
     339        End Function
     340
     341        Const Function IndexOf(c As StrChar, start As Long) As Long
     342            rangeCheck(start)
     343            Return indexOfCore(c, start, m_Length - start)
     344        End Function
     345
     346        Const Function IndexOf(c As StrChar, start As Long, count As Long) As Long
     347            rangeCheck(start, count)
     348            Return indexOfCore(c, start, count)
     349        End Function
     350    Private
     351        Const Function indexOfCore(c As StrChar, start As Long, count As Long) As Long
     352            indexOfCore = ActiveBasic.Strings.ChrFind(VarPtr(Chars[start]), count, c)
     353            If indexOfCore <> -1 Then
     354                indexOfCore += start
     355            End If
     356        End Function
     357    Public
     358        Const Function IndexOf(s As String) As Long
     359            Return IndexOf(s, 0, m_Length)
     360        End Function
     361
     362        Const Function IndexOf(s As String, startIndex As Long) As Long
     363            Return IndexOf(s, startIndex, m_Length - startIndex)
     364        End Function
     365
     366        Const Function IndexOf(s As String, startIndex As Long, count As Long) As Long
     367            rangeCheck(startIndex, count)
     368            If Object.ReferenceEquals(s, Nothing) Then
     369                'Throw New ArgumentNullException
     370                Debug
     371            End If
     372
     373            Dim length = s.Length
    383374            If length = 0 Then Return startIndex
    384375
     
    386377            For i = startIndex To startIndex + count - 1
    387378                For j = 0 To length - 1
    388                     If Chars[i + j] = lpszText[j] Then
     379                    If Chars[i + j] = s[j] Then
    389380                        If j = length - 1 Then Return i
    390381                    Else
     
    396387        End Function
    397388
    398         Const Function LastIndexOf(lpszText As *StrChar) As Long
    399             Return LastIndexOf(lpszText, m_Length - 1, m_Length)
    400         End Function
    401 
    402         Const Function LastIndexOf(lpszText As *StrChar, startIndex As Long) As Long
    403             Return LastIndexOf(lpszText As *StrChar, startIndex, startIndex + 1)
    404         End Function
    405 
    406         Const Function LastIndexOf(lpszText As *StrChar, startIndex As Long, count As Long) As Long
    407             Dim length = lstrlen(lpszText)
    408 
    409             If startIndex < 0 Or startIndex > m_Length - 1 Then Return -1
    410             If count < 1 Or count > startIndex + 2 Then Return -1
     389        Const Function LastIndexOf(s As String) As Long
     390            Return LastIndexOf(s, m_Length - 1, m_Length)
     391        End Function
     392
     393        Const Function LastIndexOf(s As String, startIndex As Long) As Long
     394            Return LastIndexOf(s, startIndex, startIndex + 1)
     395        End Function
     396
     397        Const Function LastIndexOf(s As String, startIndex As Long, count As Long) As Long
     398            If Object.ReferenceEquals(s, Nothing) Then
     399                'Throw New ArgumentNullException
     400                Debug
     401            End If
     402
     403            If startIndex < 0 Or startIndex > m_Length - 1 Or _
     404                count < 0 Or count > startIndex + 2 Then
     405                'Throw New ArgumentOutOfRangeException
     406                Debug
     407            End If
     408            Dim length = s.Length
    411409            If length > m_Length Then Return -1
    412 
    413410            If length = 0 Then Return startIndex
    414411
     
    416413            For i = startIndex To  startIndex - count + 1 Step -1
    417414                For j = length - 1 To 0 Step -1
    418                     If Chars[i + j] = lpszText[j] Then
     415                    If Chars[i + j] = s[j] Then
    419416                        If j = 0 Then Return i
    420417                    Else
     
    426423        End Function
    427424
    428         Const Function StartsWith(lpszText As *StrChar) As Boolean
    429             Return IndexOf(lpszText) = 0
    430         End Function
    431 
    432         Const Function EndsWith(lpszText As *StrChar) As Boolean
    433             Return LastIndexOf(lpszText) = m_Length - lstrlen(lpszText)
     425        Const Function StartsWith(s As String) As Boolean
     426            Return IndexOf(s) = 0
     427        End Function
     428
     429        Const Function EndsWith(s As String) As Boolean
     430            Return LastIndexOf(s) = m_Length - s.Length
    434431        End Function
    435432
    436433        Const Function Insert(startIndex As Long, text As String) As String
    437             Return Insert(startIndex, text.Chars, text.Length)
    438         End Function
    439 
    440         Const Function Insert(startIndex As Long, text As *StrChar) As String
    441             Return Insert(startIndex, text, lstrlen(text))
    442         End Function
    443 
    444         Const Function Insert(startIndex As Long, text As *StrChar, length As Long) As String
    445             If startIndex < 0 Or startIndex > m_Length Or length < 0 Then
    446                 Debug 'ArgumentOutOfRangeException
    447 
    448             End If
    449             Insert = New String(m_Length + length)
    450             memcpy(Insert.Chars, Chars, SizeOf (StrChar) * startIndex)
    451             memcpy(VarPtr(Insert.Chars[startIndex]), text, SizeOf (StrChar) * length)
    452             memcpy(VarPtr(Insert.Chars[startIndex + length]), VarPtr(Chars[startIndex]), SizeOf (StrChar) * (m_Length - startIndex + 1))
    453         End Function
    454 
    455         Const Function SubString(startIndex As Long) As String
    456             Return SubString(startIndex, m_Length - startIndex)
    457         End Function
    458 
    459         Const Function SubString(startIndex As Long, length As Long) As String
    460             If startIndex < 0 Or length <= 0 Then Return ""
    461             If startIndex + length > m_Length Then Return ""
    462 
    463             Dim temp As String
    464             temp.AllocStringBuffer(length)
    465             memcpy(temp.Chars, VarPtr(Chars[startIndex]), SizeOf (StrChar) * length)
    466             temp.Chars[length] = 0
    467             Return temp
     434            Dim sb = New System.Text.StringBuilder(This)
     435            sb.Insert(startIndex, text)
     436            Return sb.ToString
     437        End Function
     438
     439        Const Function Substring(startIndex As Long) As String
     440            rangeCheck(startIndex)
     441            Return Substring(startIndex, m_Length - startIndex)
     442        End Function
     443
     444        Const Function Substring(startIndex As Long, length As Long) As String
     445            rangeCheck(startIndex, length)
     446            Return New String(Chars, startIndex, length)
    468447        End Function
    469448
    470449        Const Function Remove(startIndex As Long) As String
    471             If startIndex < 0 Or startIndex > m_Length Then
    472                 Debug 'ArgumentOutOfRangeException
    473             End If
    474 
    475             Remove = New String(startIndex)
    476             memcpy(Remove.Chars, This.Chars, SizeOf (StrChar) * startIndex)
     450            rangeCheck(startIndex)
     451            Remove = Substring(0, startIndex)
    477452        End Function
    478453
    479454        Const Function Remove(startIndex As Long, count As Long) As String
    480             If startIndex < 0 Or count < 0 Or startIndex + count > m_Length Then
    481                 Debug 'ArgumentOutOfRangeException
    482             End If
    483 
    484             Remove = New String(m_Length - count)
    485             memcpy(Remove.Chars, This.Chars, SizeOf (StrChar) * startIndex)
    486             memcpy(VarPtr(Remove.Chars[startIndex]), VarPtr(This.Chars[startIndex + count]), SizeOf (StrChar) * (m_Length - startIndex - count))
     455            Dim sb = New System.Text.StringBuilder(This)
     456            sb.Remove(startIndex, count)
     457            Remove = sb.ToString
    487458        End Function
    488459
     
    497468
    498469        Const Function Replace(oldChar As StrChar, newChar As StrChar) As String
    499             Replace = Copy(This)
    500             With Replace
    501                 Dim i As Long
    502                 For i = 0 To ELM(.m_Length)
    503                     If .Chars[i] = oldChar Then
    504                         .Chars[i] = newChar
    505                     End If
    506                 Next
    507             End With
    508         End Function
    509 
    510         Const Function Replace(ByRef oldStr As String, ByRef newStr As String) As String
    511     '       If oldStr = Nothing Then Throw ArgumentNullException
    512     '
    513     '       If newStr = Nothing Then
    514     '           Return ReplaceCore(oldStr, oldStr.m_Length, "", 0)
    515     '       Else
    516                 Return ReplaceCore(oldStr, oldStr.m_Length, newStr, newStr.m_Length)
    517     '       End If
    518         End Function
    519 
    520         Const Function Replace(oldStr As *StrChar, newStr As *StrChar) As String
    521             If oldStr = 0 Then Debug 'Throw ArgumentNullException
    522             If newStr = 0 Then newStr = ""
    523             Return ReplaceCore(oldStr, lstrlen(oldStr), newStr, lstrlen(newStr))
    524         End Function
    525 
    526         Const Function Replace(oldStr As *StrChar, oldLen As Long, newStr As *StrChar, newLen As Long) As String
    527             If oldStr = 0 Then Debug 'Throw ArgumentNullException
    528             If newStr = 0 Then
    529                 newStr = ""
    530                 newLen = 0
    531             End If
    532             Return ReplaceCore(oldStr, oldLen, newStr, newLen)
     470            Dim sb = New System.Text.StringBuilder(This)
     471            sb.Replace(oldChar, newChar)
     472            Replace = sb.ToString
     473        End Function
     474
     475        Const Function Replace(oldStr As String, newStr As String) As String
     476            Dim sb = New System.Text.StringBuilder(This)
     477            sb.Replace(oldStr, newStr)
     478            Return sb.ToString
    533479        End Function
    534480
    535481        Const Function ToLower() As String
    536             ToLower.ReSize(m_Length)
     482            Dim sb = New System.Text.StringBuilder(m_Length)
     483            sb.Length = m_Length
    537484            Dim i As Long
    538485            For i = 0 To ELM(m_Length)
    539                 ToLower.Chars[i] = _System_ASCII_ToLower(Chars[i])
     486                sb[i] = _System_ASCII_ToLower(Chars[i])
    540487            Next
     488            Return sb.ToString
    541489        End Function
    542490
    543491        Const Function ToUpper() As String
    544             ToUpper.ReSize(m_Length)
     492            Dim sb = New System.Text.StringBuilder(m_Length)
     493            sb.Length = m_Length
    545494            Dim i As Long
    546495            For i = 0 To ELM(m_Length)
    547                 ToUpper.Chars[i] = _System_ASCII_ToUpper(Chars[i])
     496                sb[i] = _System_ASCII_ToUpper(Chars[i])
    548497            Next
    549         End Function
    550     /*
    551         Sub Swap(ByRef x As String)
    552             Dim tempLen As Long
    553             Dim tempChars As *StrChar
    554             tempLen = x.m_Length
    555             tempChars = x.Chars
    556             x.m_Length = This.m_Length
    557             x.Chars = This.Chars
    558             This.m_Length = tempLen
    559             This.Chars = tempChars
    560         End Sub
    561     */
     498            Return sb.ToString
     499        End Function
     500
    562501        Override Function ToString() As String
    563             Return This
    564         End Function
    565 
     502            ToString = This
     503        End Function
     504
     505        Const Function Clone() As String
     506            Clone = This
     507        End Function
    566508        Static Function Copy(s As String) As String
    567             Copy.ReSize(s.m_Length)
    568             memcpy(Copy.Chars, This.Chars, SizeOf (StrChar) * m_Length)
    569         End Function
     509            Copy = New String(s.Chars, s.m_Length)
     510        End Function
     511
     512        Sub CopyTo(sourceIndex As Long, destination As *StrChar, destinationIndex As Long, count As Long)
     513            ActiveBasic.Strings.ChrCopy(VarPtr(destination[destinationIndex]), VarPtr(Chars[sourceIndex]), count As SIZE_T)
     514        End Sub
    570515
    571516        Override Function GetHashCode() As Long
     
    577522            Return _System_GetHashFromWordArray(Chars As *Word, size)
    578523        End Function
     524
     525        Function PadLeft(total As Long) As String
     526            PadLeft(total, &h30 As StrChar)
     527        End Function
     528
     529        Function PadLeft(total As Long, c As StrChar) As String
     530            If total < 0 Then
     531                'Throw New ArgumentException
     532            End If
     533            If total >= m_Length Then
     534                Return This
     535            End If
     536            Dim sb = New System.Text.StringBuilder(total)
     537            sb.Append(c, total - m_Length)
     538            sb.Append(This)
     539            Return sb.ToString
     540        End Function
     541
     542        Function PadRight(total As Long) As String
     543            PadLeft(total, &h30 As StrChar)
     544        End Function
     545
     546        Function PadRight(total As Long, c As StrChar) As String
     547            If total < 0 Then
     548                'Throw New ArgumentException
     549            End If
     550            If total >= m_Length Then
     551                Return This
     552            End If
     553            Dim sb = New System.Text.StringBuilder(total)
     554            sb.Append(This)
     555            sb.Append(c, total - m_Length)
     556            Return sb.ToString
     557        End Function
    579558    Private
    580         ' メモリ確保に失敗すると元の文字列は失われない。(例外安全でいう強い保障)
    581559        Function AllocStringBuffer(textLength As Long) As *StrChar
    582560            If textLength < 0 Then
    583561                Return 0
    584             ElseIf textLength > m_Length or Chars = 0 Then
    585                 AllocStringBuffer = _System_realloc(Chars, SizeOf(StrChar) * (textLength + 1))
    586                 If AllocStringBuffer <> 0 Then
    587                     m_Length = textLength
    588                     Chars = AllocStringBuffer
    589                 End If
    590             Else
    591                 m_Length = textLength
    592                 AllocStringBuffer = Chars
    593             End If
    594         End Function
    595 
    596         Function ReplaceCore(oldStr As *StrChar, oldLen As Long, newStr As *StrChar, newLen As Long) As String
    597             If oldLen = 0 Then
    598                 Debug 'Throw ArgumentException
    599             End If
    600             Dim tmp As String
    601             With tmp
    602                 Dim current = 0 As Long
    603                 Do
    604                     Dim pos = IndexOf(oldStr, current)
    605                     If pos = -1 Then
    606                         Exit Do
    607                     End If
    608                     .Append(VarPtr(Chars[current]), pos - current)
    609                     .Append(newStr, newLen)
    610                     current = pos + oldLen
    611                 Loop
    612                 .Append(VarPtr(Chars[current]), m_Length - current)
    613             End With
    614             Return tmp
     562            End If
     563            AllocStringBuffer = GC_malloc_atomic(SizeOf(StrChar) * (textLength + 1))
     564            If AllocStringBuffer = 0 Then
     565                'Throw New OutOfMemoryException
     566            End If
     567            m_Length = textLength
     568            Chars = AllocStringBuffer
    615569        End Function
    616570
    617571        Sub AssignFromStrChar(text As *StrChar, textLength As Long)
    618             If text = Chars Then Exit Sub
    619             If AllocStringBuffer(textLength) <> 0 Then
    620                 memcpy(Chars, text, SizeOf (StrChar) * textLength)
    621                 Chars[m_Length] = 0
     572            AllocStringBuffer(textLength)
     573            ActiveBasic.Strings.ChrCopy(Chars, text, textLength As SIZE_T)
     574            Chars[m_Length] = 0
     575        End Sub
     576
     577        Const Sub rangeCheck(index As Long)
     578            If index < 0 Or index > m_Length Then
     579                Debug 'ArgumentOutOfRangeException
     580            End If
     581        End Sub
     582       
     583        Const Sub rangeCheck(start As Long, length As Long)
     584            If start < 0 Or start > This.m_Length Or length < 0 Then
     585                Debug 'ArgumentOutOfRangeException
    622586            End If
    623587        End Sub
Note: See TracChangeset for help on using the changeset viewer.