source: trunk/Include/Classes/System/IO/Path.ab @ 435

Last change on this file since 435 was 429, checked in by OverTaker, 15 years ago

System/IO/Path.ab再実装。

File size: 7.4 KB
Line 
1/*!
2@file   Classes/System/IO/Path.ab
3@brief  ファイルパス文字列を操作する
4@author OverTaker
5*/
6
7Namespace System
8Namespace IO
9
10Class Path
11Public
12    Static Const AltDirectorySeparatorChar = &H2F As StrChar '/
13    Static Const DirectorySeparatorChar    = &H5C As StrChar '\
14    Static Const PathSeparator             = &H3B As StrChar ';
15    Static Const VolumeSeparatorChar       = &H3A As StrChar ':
16
17    '----------------------------------------------------------------
18    ' パブリック メソッド
19    '----------------------------------------------------------------
20
21    /*
22    @brief  拡張子を変更する
23    @param  パス
24    @param  変更する拡張子(.を含む)
25    @return 拡張子変更後のパス
26    */
27    Static Function ChangeExtension(path As String, extension As String) As String
28        path = CheckPath(path)
29        If HasExtension(path) Then
30            Return path.Remove(GetExtensionIndex(path)) + extension
31        Else
32            Return path + extension
33        End If
34    End Function
35
36    /*
37    @brief  二つのパスを結合する
38    @param  結合されるパス
39    @param  結合するパス
40    @return パス
41    */
42    Static Function Combine(path1 As String, path2 As String) As String
43        path1 = CheckPath(path1)
44        path2 = CheckPath(path2)
45        If IsPathRooted(path2) Then
46            Return path2
47        Else
48            If Not path1.EndsWith(DirectorySeparatorChar) Then
49                path1 += Chr$(DirectorySeparatorChar)
50            End If
51            Return path1 + path2
52        End If
53    End Function
54
55    /*
56    @brief  パス文字列からファイル名を取得する
57    @param  パス
58    @return ファイル名
59    */
60    Static Function GetFileName(path As String) As String
61        path = CheckPath(path)
62        Dim lastSeparatorIndex = GetLastSeparatorIndex(path) As Long
63        If lastSeparatorIndex <> -1 Then
64            Return path.Substring(lastSeparatorIndex + 1)
65        Else
66            Return path
67        End If
68    End Function
69
70    /*
71    @brief  パス文字列からファイル名を拡張子を除いて取得する
72    @param  パス
73    @return 拡張子を除いたファイル名
74    */
75    Static Function GetFileNameWithoutExtension(path As String) As String
76        path = GetFileName(path)
77        If HasExtension(path) Then
78            Return path.Remove(GetExtensionIndex(path))
79        Else
80            Return path
81        End If
82    End Function
83
84    /*
85    @brief  絶対パスを取得する
86    @param  相対パス
87    @return 絶対パス
88    */
89    Static Function GetFullPath(path As String) As String
90        Return Combine(System.Environment.CurrentDirectory, path)
91    End Function
92
93    /*
94    @brief  パス文字列から拡張子を取得する
95    @param  パス
96    @return .を含む拡張子
97    */
98    Static Function GetExtension(path As String) As String
99        path = CheckPath(path)
100        Dim extensionIndex = GetExtensionIndex(path)
101        If extensionIndex <> -1 Then
102            Return path.Substring(extensionIndex)
103        Else
104            Return New String()
105        End If
106    End Function
107
108    /*
109    @brief  ひとつ上のディレクトリを取得する
110    @param  パス
111    @return ディレクトリパス
112    */
113    Static Function GetDirectoryName(path As String) As String
114        path = CheckPath(path)
115        Dim lastSeparatorIndex = GetLastSeparatorIndex(path)
116        If lastSeparatorIndex = -1 Then
117            Return New String()
118        Else
119            Return path.Substring(0, lastSeparatorIndex)
120        End If
121    End Function
122
123    /*
124    @brief  ルートディレクトリを取得する
125    @param  パス
126    @return ルートディレクトリ
127    */
128    Static Function GetPathRoot(path As String) As String
129        path = CheckPath(path)
130        If IsPathRooted(path) Then
131            If path.Contains(UniformNamingConventionString) Then
132                Return path.Remove(path.IndexOf(DirectorySeparatorChar,
133                                                      UniformNamingConventionString.Length) + 1)
134            Else
135                Return path.Remove(3)
136            End If
137        Else
138            Return New String()
139        End If
140    End Function
141
142    /*!
143    @brief  ランダムなファイル名を取得する
144    @param  ファイルパス
145    @return ファイル名
146    手抜き実装
147    */
148    Static Function GetRandomFileName() As String
149        Randomize
150        Return Str$(((Rnd() * 900000000) As Long) + 10000000)
151    End Function
152
153    /*!
154    @brief  一時ファイルを作成し、ファイルパスを取得する
155    @return パス
156    */
157    Static Function GetTempFileName() As String
158        Dim tempFileName[ELM(MAX_PATH)] As TCHAR
159        Dim len = WIN32API_GetTempFileName(GetTempPath(), "ABT", 0, tempFileName)
160        If len <> 0 Then
161            Return New String(tempFileName, len As Long)
162        Else
163            Throw New IOException("Path.GetTempFileName: Failed to GetTempFileName.")
164        End If
165    End Function
166
167
168    /*
169    @brief  システムの一時フォルダのパス取得する
170    @return パス
171    */
172    Static Function GetTempPath() As String
173        Dim size = WIN32API_GetTempPath(0, 0)
174        Dim p = GC_malloc_atomic(SizeOf (TCHAR) * size) As PCTSTR
175        Dim len = WIN32API_GetTempPath(size, p)
176        If (len > size) or len = 0 Then
177            Throw New IOException("Path.GetTempPath: Failed to GetTempPath.")
178        Else
179            Return New String(p, len As Long)
180        End If
181    End Function
182
183
184    /*
185    @brief  パスに拡張子が含まれるかどうか
186    @param  パス
187    @retval True  含まれる
188    @retval False 含まれない
189    */
190    Static Function HasExtension(path As String) As Boolean
191        path = CheckPath(path)
192        Return GetExtensionIndex(path) <> -1
193    End Function
194
195    /*
196    @brief  パスが絶対パスか取得する
197    @param  パス
198    @retval True  絶対パス
199    @retval False 相対パス
200    */
201    Static Function IsPathRooted(path As String) As Boolean
202        path = CheckPath(path)
203        Return path.Contains(UniformNamingConventionString) _
204            or path.Contains(VolumeSeparatorChar) _
205            or path.StartsWith(DirectorySeparatorChar)
206    End Function
207
208Private
209    Static Const ExtensionSeparatorChar = &H2E As StrChar
210    Static Const InvalidPathChars = Ex"\q<>|\0\t" As String
211    Static Const UniformNamingConventionString = Ex"\\\\" As String
212
213    '----------------------------------------------------------------
214    ' プライベート メソッド
215    '----------------------------------------------------------------
216
217    /*
218    @brief  パスに不正な文字が含まれていないか調べる。
219    @param  パス
220    @return 正しく直されたパス
221    パス末端にディレクトリ区切り記号があった場合除去する
222    ..\などが含まれるパスについては未実装
223    */
224    Static Function CheckPath(path As String) As String
225        path = path.Replace(AltDirectorySeparatorChar, DirectorySeparatorChar)
226
227        Dim i As Long
228        For i = 0 To ELM(InvalidPathChars.Length)
229            If path.Contains(InvalidPathChars.Substring(i, 1)) Then
230                Throw New IOException("Path.CheckPath: The path contains invalidPathChars.")
231            End If
232        Next
233
234        If path.LastIndexOf(UniformNamingConventionString) > 0 Then
235            Throw New IOException("Path.CheckPath: The path is invalid value.")
236        End If
237
238        If path.EndsWith(DirectorySeparatorChar) Then
239            Return path.Remove(path.Length - 1)
240        Else
241            Return path
242        End If
243    End Function
244
245    /*
246    @brief  パスの最も後ろにあるディレクトリ区切り記号の位置を取得する
247    @param  パス
248    @return インデックス
249    */
250    Static Function GetLastSeparatorIndex(path As String) As Long
251        Return System.Math.Max(path.LastIndexOf(DirectorySeparatorChar),
252                               path.LastIndexOf(AltDirectorySeparatorChar)) As Long
253    End Function
254
255    /*
256    @brief  拡張子の位置を取得する。
257    @param  パス
258    @return インデックス
259    */
260    Static Function GetExtensionIndex(path As String) As Long
261        Dim extensionIndex = path.LastIndexOf(ExtensionSeparatorChar) As Long
262        If extensionIndex > GetLastSeparatorIndex(path) Then
263            Return extensionIndex
264        Else
265            Return -1
266        End If
267    End Function
268End Class
269
270'メソッドと名前が被るAPI
271Function WIN32API_GetTempPath(nBufferLength As DWord, lpBuffer As PTSTR) As DWord
272    Return GetTempPath(nBufferLength, lpBuffer)
273End Function
274
275Function WIN32API_GetTempFileName (pPathName As PCTSTR, pPrefixString As PCTSTR, uUnique As DWord, pTempFileName As PTSTR) As DWord
276    Return GetTempFileName(pPathName, pPrefixString, uUnique, pTempFileName)
277End Function
278
279
280End Namespace
281End Namespace
Note: See TracBrowser for help on using the repository browser.