Что нового

Общая переменная для всего скрипта

Viktor1703

AutoIT Гуру
Сообщения
1,535
Репутация
413
Не знаю, окажется ли кому нибудь полезным такой вариант обращения с массивом, но мне он оказался полезным, смысл в том что можно создать один безразмерный массив (но в смысле в меру, до 999.999) и записывать в него данные в мною так называемые ячейки, а потом по ходу выполнения скрипта их просто считывать, для меня оказалось удобным такое решение.

Код:
Global $Array = _ArrayS_Create() ; Создаём первый массив
_ArrayS_WriteData($Array, 8, "Hello") ; Записываем данные 
_ArrayS_WriteData($Array, 2, "Example") ; Записываем данные 

MsgBox(0, "Index 8", _ArrayS_ReadData($Array, 8)) ; Считываем данные 

_ArrayS_ReplaceData($Array, 8, "5743") ; Заменяем данные в ячейке 8 на "5743"
MsgBox(0, "Index 8", _ArrayS_ReadData($Array, 8)) ; Считываем данные

_ArrayS_RemoveData($Array, 8) ; Стираем данные из 8й ячейки
MsgBox(0, "Index 8", _ArrayS_ReadData($Array, 8)) ; Считываем данные

_ArrayS_CopyData($Array, 2, 8) ; Копируем данные из 2й ячейки в 8ю
MsgBox(0, "Index 8", _ArrayS_ReadData($Array, 8)) ; Считываем данные

_ArrayS_ReplaceData($Array, 8, "Hello") ; Заменяем данные в ячейке 8 на Hello
$index = _ArrayS_ExistsData($Array, "Hello") ; проверяем на существование данного слова в массиве
MsgBox(0, "Exists", "Exists Data = " & $index[0] & @CRLF & "Index Data = " & $index[1]) ; Считываем данные "Exists Data" если 1 то такое слово есть в массиве, "Index" индекс (ячейка) в котором находится это слово

MsgBox(0, "Size", "Array Size = " & _ArrayS_GetSize($Array) & " байт") ; Смотрим сколько байт весит наш массив
MsgBox(0, "List", _ArrayS_ListData($Array)) ; Выводим весь массив

Global $Array2 = _ArrayS_Create() ; Создаём 2й массив
_ArrayS_WriteData($Array2, 1, "2й массив") ; Записываем данные в масив в 1ю ячейку
MsgBox(0, "Index 8", _ArrayS_ReadData($Array, 8)) ; Читаем данные из первого массива
MsgBox(0, "Index 8", _ArrayS_ReadData($Array2, 1)); Читаем данные из второго массива
MsgBox(0, "Index 2", _ArrayS_ReadData($Array, 2)) ; Читаем данные из первого массива


Func _ArrayS_Create()
	Local $Array[1] = [""]
	Return $Array
EndFunc	

Func _ArrayS_WriteData(ByRef $Array, $Index, $Value)
	Local $Col 
	If IsArray($Array) Then
		For $i = 0 To UBound($Array) - 1
			$Col = $i
		Next
        If $Col < $Index Then
		    $Array[0] += $Index
		    ReDim $Array[$Array[0] + $Index]
		    $Array[$Array[0]] = $Value
		ElseIf $Col >= $Index Then
			If $Array[$Index] = "" Then 
			    $Array[$Index] = $Value
			EndIf	
		EndIf	
	EndIf	
EndFunc

Func _ArrayS_ReplaceData(ByRef $Array, $Index, $Value)
	If IsArray($Array) Then
		For $i = 0 To UBound($Array) - 1
			If $Index = $i Then 
				If $Value <> "" Then
				    $Array[$i] = $Value
				    Return 1
				EndIf	
			EndIf	
		Next
        Return 0		
	EndIf	
EndFunc

Func _ArrayS_RemoveData(ByRef $Array, $Index)
	If IsArray($Array) Then
		For $i = 0 To UBound($Array) - 1
			If $Index = $i Then 
				$Array[$i] = ""
				Return 1
			EndIf	
		Next
        Return 0		
	EndIf	
EndFunc

Func _ArrayS_CopyData(ByRef $Array, $Index, $Copy)
	Local $ArrayData
	If IsArray($Array) Then
		For $i = 0 To UBound($Array) - 1
			If $Index = $i Then 
				$ArrayData = $Array[$i]
			EndIf	
		Next
		For $i = 0 To UBound($Array) - 1
		    If $Copy = $i Then
			    $Array[$i] = $ArrayData
			    Return 1
		    EndIf
		Next	
        Return 0		
	EndIf	
EndFunc

Func _ArrayS_ReadData(ByRef $Array, $Index)
	If IsArray($Array) Then
		For $i = 0 To UBound($Array) - 1
			If $Index = $i Then 
	            Return $Array[$i]
			EndIf	
		Next
		Return 0
	EndIf	
EndFunc	

Func _ArrayS_ListData(ByRef $Array)
	Local $ArrayList
	If IsArray($Array) Then
		For $i = 1 To UBound($Array) - 1
			If $Array[$i] <> "" Then
			    $ArrayList &= $Array[$i] & @CRLF
			EndIf	
		Next
		Return $ArrayList
	EndIf	
EndFunc	

Func _ArrayS_ExistsData(ByRef $Array, $Value)
	Local $Ret[2]
	If IsArray($Array) Then
		For $i = 1 To UBound($Array) - 1
			If $Array[$i] = $Value Then 
				$Ret[0] = 1
				$Ret[1] = $i
				Return $Ret			
			EndIf	
		Next
		$Ret[0] = 0
		$Ret[1] = 0
		Return $Ret	
	EndIf	
EndFunc

Func _ArrayS_GetSize(ByRef $Array)
	Local $ArraySize
	If IsArray($Array) Then
		For $i = 1 To UBound($Array) - 1
			$ArraySize += (StringLen($Array[$i]) * 2)
		Next
	EndIf
	Return $ArraySize
EndFunc

Func _ArrayS_Delete(ByRef $Array)
	If IsArray($Array) Then
		For $i = 0 To UBound($Array) - 1
			$Array[$i] = ""
		Next
	EndIf	
EndFunc
 

Yashied

Модератор
Команда форума
Глобальный модератор
Сообщения
5,379
Репутация
2,717
Вопрос, зачем? Все эти бесчисленные проверки, ReDim'ы и т.д. явно не прибавят производительности коду. Как правило, если есть много логически связанных переменных, например параметры файла, то создают 2D массив с размером (количеством столбцов) равным количеству файлов, а в каждую строку помещают эти самые параметры.

Совет. Не далайте ReDim на 1 единицу, т.к. ReDim сам по себе довольно медленный. Лучше создать заведомо больший массив, например 500 единиц, а по достижении этого значения сделать ReDim еще на 500 единиц. Этим вы увеличите скорость в несколько раз.
 
Автор
V

Viktor1703

AutoIT Гуру
Сообщения
1,535
Репутация
413
Понял, спасибо за совет, я про ReDim инфу не читал, по этому не знаю как работает, ну попробую как то довести до нормального, хотя нужно ли....
 

Yashied

Модератор
Команда форума
Глобальный модератор
Сообщения
5,379
Репутация
2,717
Вообще, если взять любую из моих библиотек, например Pop-ups.au3, то в начале файла можно увидеть примерно такие строки:

Код:
Dim $ppData[1][16] = [[0, GUICreate(''), DllCallbackRegister('_pp_Timer', 'none', ''), 0, 1, 1, 10, 0, 0]]

#cs

$ppData[0][0 ]   - Number of items in array
       [0][1 ]   - Handle to the pop-up root owner window
       [0][2 ]   - Handle to the timer function
       [0][3 ]   - Timer ID
       [0][4 ]   - Timer control flag (External)
       [0][5 ]   - Timer control flag (Internal)
       [0][6 ]   - The time-out to update
       [0][7 ]   - Update mode (0 - Timer; 1 - User)
       [0][8-15] - Don`t used

$ppData[i][0 ]   - Handle to the pop-up window
       [i][1 ]   - Handle to the bitmap
       [i][2 ]   - The x-coordinate of the center of the pop-up window ((-1) - Center of the desktop screen)
       [i][3 ]   - The y-coordinate of the center of the pop-up window ((-1) - Center of the desktop screen)
       [i][4 ]   - Time of show the pop-up window, in milliseconds (0 - Disabled; (-1) - Permanent)
       [i][5 ]   - Time of fade-out for the pop-up window, in milliseconds
       [i][6 ]   - Destroy bitmap control flag
       [i][7 ]   - The callback function ("" - None)
       [i][8 ]   - $tagSIZE structure that contains the bitmap dimension
       [i][9 ]   - Pop-up window initialization control flag
       [i][10]   - Pop-up window active (show) flag
       [i][11]   - Pop-up window fade-out flag
       [i][12]   - A timestamp for the show pop-up window
       [i][13]   - A timestamp for the fade-out
       [i][14]   - Opacity value
       [i][15]   - Reserved

#ce


Далее я работаю с этим массивом как с отдельными переменными. Делать лишнюю обертку для этого явно не имеет смысла.
 
Автор
V

Viktor1703

AutoIT Гуру
Сообщения
1,535
Репутация
413
Да, я видел Ваши примеры, например Skin.au3, я просто редко когда работаю с массивами и особенно с ReDim'ом, по этому не ещё не понял всех тонкостей, буду исправлятся :smile:
 

AZJIO

Меценат
Меценат
Сообщения
2,764
Репутация
1,153
Viktor1703
ReDim с массивом до 1000 работает достаточно быстро, чтоб с ним заморачиваться, а при 100000 это уже настоящий тормоз. Это проверяется просто, секундомер из TimerInit и цикл с многократным ReDim.

Код:
Dim $aM[1]
$z=0
$timer = TimerInit()
For $i = 1 to 1000
	ReDim $aM[$i]
	; $z+=1
Next
MsgBox(0,"Время выполнения ReDim", 'Массив aM= '&UBound($aM) &@CRLF&'z= '&$z&@CRLF&Round(TimerDiff($timer) / 1000, 2) & ' сек')

; 1-1000 ReDim - 0.01 сек
; 1-10000 ReDim - 0.97 сек
; 99000-100000 ReDim - 1.92 сек (1000 ReDim при величине массива 100000 выполняется заметно дольше)
; 999980-1000000 ReDim - 0.41 сек  (20 ReDim при величине массива 1000000)

; 1-100 000 $z+=1 - 0.02 сек - тест примитивного цикла для проверки погрешности добавляемой самим циклом.
; 1-1000 000 $z+=1 - 0.23 сек


Кстати всё что я выкладываю есть в коллекции
 
Автор
V

Viktor1703

AutoIT Гуру
Сообщения
1,535
Репутация
413
Спасибо за пример, теперь визуально вижу что не стоит так заморачиватся ради 10 простых функций, аналогов куча, просто хотелось как то упростить, а получилось на оборот :smile:

Можно тогда тему удалить, чтоб не мешалась?
 
Верх