#include-once
; =======================================
; Title .........: _Array_Dump
; AutoIt Version : 3.3.2.0+
; Language ......: Русский
; Description ...: Дамп массивов.
; Version .......: 1.1
; =======================================

; #CURRENT# =============================
; _Array_Dump
; =======================================

; Внутренние функции
; #INTERNAL_USE_ONLY#====================
; __Array_Dump_Value
; =======================================

; ============================================================================================
; Имя функции ...: _Array_Dump
; Версия AutoIt .: 3.3.2.0+
; Описание ......: Сохраняет структуру массива в файл или выводит в консоль
; Синтаксис......: _Array_Dump($array, $array_name, $file_name = False, $func_prefix = 'dump_')
; Параметры......: $array - массив, который необходимо сохранить
; Параметры.....: $array_name - имя массива
; Параметры......: $file_name - помещать ли результат в файл, если да - то указывается имя файла
; Параметры......: $func_prefix - префикс имени итоговой функции
; Параметры......: $comments - включить, выключить комментарии
; Возвращаемое значение:
;					|Успешно -  Возвращает True или False если указано имя файла иначе возвращает итоговый результат
;					|Неудачно - 0
; Автор ..........: inververs
; Примечания ..: Функция полностью воссоздает структуру переданного массива и помещает результат в функцию.
; Размерность массивов не ограничена. Поддерживает неограниченную вложенность массивов друг в друга.
; Сохраняет следующие значения: строки, числа, ключевые слова, булев тип. Все остальные типы данных обрамляются одинарной кавычкой.
; Примерю..........: ConsoleWrite(_Array_Dump(StringSplit(123,''),'split') & @LF)
; ============================================================================================
Func _Array_Dump($array, $array_name, $file_name = False, $func_prefix = 'dump_', $comments = True)
	If Not IsArray($array) Then Return SetError(1, 0, 0)

	If $file_name = Default Then $file_name = False
	If $func_prefix = Default Then $func_prefix = 'dump_'
	If $comments = Default Then $comments = True

	Local Static $level = 0
	Local Static $result_before
	Local Static $var_count = 0

	Local $result_after
	Local $size_string

	Local $rang = UBound($array, 0)
	Local $count = 1
	For $i = 1 To $rang
		$count *= UBound($array, $i)
		$size_string &= '[' & UBound($array, $i) & ']'
	Next

	Local $result, $position, $size, $result_2, $value, $var_name, $return, $var_comment, $comment

	For $index = 0 To $count - 1
		$position = $index
		$result = ''
		For $i = $rang To 1 Step -1
			$size = UBound($array, $i)
			$result = '[' & Mod($position, $size) & ']' & $result
			$position = Floor($position / $size)
		Next

		$value = Execute('$array' & $result)

		If IsArray($value) Then
			$level += 1

			$var_name = $array_name & '_' & StringFormat('%02d', $var_count)
			$var_count += 1

			$result_2 = _Array_Dump($value, $var_name, $file_name, $func_prefix, $comments)
			$level -= 1

			If $comments Then
				$var_comment = StringRegExp($result_2, '(\[.+\])', 1);
				$comment = @TAB & '    ; ' & VarGetType($value) & '' & $var_comment[0]
			EndIf
			$result_before &= $result_2 & @CRLF
			$result_after &= '    ' & '$' & $array_name & $result & ' = $' & $var_name & $comment & @CRLF
		Else
			$var_comment = __Array_Dump_Value($value)

			If $comments Then
				$comment = @TAB & '    ; ' & $var_comment
			EndIf

			$return = '    ' & '$' & $array_name & $result & ' = ' & $value & $comment
			$result_after &= $return & @CRLF
		EndIf
	Next
	$result_after = '    ' & 'Local $' & $array_name & $size_string & @CRLF & $result_after

	If $level = 0 Then
		Local $out = '' & _
				'Func ' & $func_prefix & $array_name & '()' & @CRLF & _
				$result_before & $result_after & @CRLF & _
				'    ' & 'Return $' & $array_name & @CRLF & _
				'EndFunc' & @CRLF & _
				'Global $' & $array_name & ' = ' & $func_prefix & $array_name & '()'

		$level = 0
		$result_before = ''
		$var_count = 0
		If $file_name Then
			Local $hFile = FileOpen($file_name, 2 + 8)
			FileWriteLine($hFile, $out)
			FileClose($hFile)
			Return @error = 0
		Else
			Return $out
		EndIf
	EndIf
	Return $result_after
EndFunc   ;==>_Array_Dump

; ============================================================================================
; Имя функции ...: __array_dump_value
; Описание ........: Экранирует значения
; Синтаксис.......: __array_dump_value($value)
; Параметры:
;		$value - значение
; Возвращаемое значение: Экранированное значение.
; Автор ..........: inververs
; Примечания ..: поддерживаются строки, ключевые слова, числа и булев тип.
; Все остальные типы данных обрамляются одинарной ковычкой.
; ============================================================================================
Func __Array_Dump_Value(ByRef $value)
	Local $var_comment = VarGetType($value)
	Select
		Case $value = Null
			$value = 'Null'
		Case IsString($value)
			$var_comment &= '(' & StringLen($value) & ')'
			$value = StringReplace($value, "'", "''")
			$value = StringReplace($value, @CRLF, "' & @CRLF & '")
			$value = StringReplace($value, @CR, "' & @CR & '")
			$value = StringReplace($value, @LF, "' & @LF & '")
			$value = "'" & $value & "'"
		Case IsKeyword($value)
		Case IsNumber($value)
		Case IsBool($value)
		Case IsBinary($value)
			$var_comment &= '(' & BinaryLen($value) & ')'
			$value = "Binary('" & $value & "')"
		Case IsFunc($value)
			$value = FuncName($value)
		Case IsObj($value)
			$var_comment &= ' не поддерживается.'
			$var_comment &= '|name:' & ObjName($value, 1)
			$var_comment &= '|Description:' & ObjName($value, 2)
			$var_comment &= '|ProgID:' & ObjName($value, 3)
			$var_comment &= '|File:' & ObjName($value, 4)
			$var_comment &= '|Module name:' & ObjName($value, 5)
			$var_comment &= '|CLSID:' & ObjName($value, 6)
			$var_comment &= '|IID:' & ObjName($value, 7)
			$value = "'" & $value & "'"
		Case IsHWnd($value)
			$value = "HWnd('" & $value & "')"
		Case IsPtr($value)
			$value = "Ptr('" & $value & "')"
		Case IsDllStruct($value)
			$var_comment &= ' не поддерживается.'
			$var_comment &= '|ptr:' & DllStructGetPtr($value)
			$var_comment &= '|size:' & DllStructGetSize($value)
			$value = "'" & $value & "'"
		Case Else
			$value = "'" & $value & "'"
	EndSelect
	$value = StringReplace($value, " & ''", '')
	$value = StringReplace($value, "'' & ", '')
	Return $var_comment
EndFunc   ;==>__Array_Dump_Value
