Всем привет знаю что это "говнокод" но всё же я в jass неопытен и поэтому прошу помощи так как сам уже устал биться. Вообщем сделал карту, добавил ботов и нижеприведённый код заставляет ботов кастовать заклинания на вражеских героев, примерно в 50% случаев игра вылетает без всяких ошибок и прочего, судя по логу из war3dbg.log ошибка в ниже приведённой функции.
Собственно вот часть лога:
000AFEAB	UNIT_TYPE_HERO
000AFEAC	IsUnitType
000AFEAD	g
000AFEAE	FirstOfGroup
000AFEAF	 	u
000AFEB0	  	AI
000AFEB1		GetOwningPlayer
000AFEB2		IsUnitEnemy
000AFEB3		AI
000AFEB4		IsUnitAliveBJ
000AFEB5		whichUnit
000AFEB6		IsUnitDeadBJ
000AFEB7		whichUnit
000AFEB8		UNIT_STATE_LIFE
000AFEB9		GetUnitState
000AFEBA	u
000AFEBB	AI
000AFEBC	GetOwningPlayer
000AFEBD	IsUnitVisible
000AFEBE	u
000AFEBF		GetUnitX
000AFEC0	u
000AFEC1	GetUnitY
000AFEC2	AI
000AFEC3	u
000AFEC4	IssueTargetOrder
А вот сама функция:
function filtgAI takes nothing returns boolean
return GetUnitState(GetFilterUnit(), UNIT_STATE_LIFE) > 0 and IsUnitType(GetFilterUnit(), UNIT_TYPE_STRUCTURE)==false and GetUnitAbilityLevel(GetFilterUnit(),'Aloc')==0 and IsUnitType(GetFilterUnit(), UNIT_TYPE_HERO)==true
endfunction

function NewAI2_system takes real distance returns nothing
local group g=CreateGroup()
local unit u=null
local unit AI=null
local real x = 0.
local real y = 0.
local real x2 = 0.
local real y2 = 0.
local integer A = 1
local integer B = 12

loop
 exitwhen A>B
  if  GetUnitState(udg_hero[A], UNIT_STATE_LIFE) > 0 and GetPlayerController(GetOwningPlayer(udg_hero[A]))==MAP_CONTROL_COMPUTER then
  set AI = udg_hero[A]
  set x = GetUnitX(AI)
  set y = GetUnitY(AI)
  call GroupEnumUnitsInRange(g,x,y,distance,Condition(function filtgAI))
  set u=FirstOfGroup(g)
  
    loop
     exitwhen u==null
      if IsUnitEnemy(u,GetOwningPlayer(AI)) == true and GetUnitState(AI, UNIT_STATE_LIFE) > 0 and IsUnitVisible(u,GetOwningPlayer(AI)) then
        set x2 = GetUnitX(u)
        set y2 = GetUnitY(u)
        call IssueTargetOrder(AI,"thunderbolt",u)
        call IssueTargetOrder(AI,"creepthunderbolt",u)
        call IssueTargetOrder(AI,"banish",u)
        call IssueTargetOrder(AI,"frostnova",u)
        call IssueTargetOrder(AI,"sleep", u)
        call IssueTargetOrder(AI,"shadowstrike",u)
        call IssueTargetOrder(AI,"chainlightning",u)
        call IssueTargetOrder(AI,"drunkenhaze",u)
        call IssueTargetOrder(AI,"acidbomb",u)
        call IssueTargetOrder(AI,"soulburn",u)
        call IssueTargetOrder(AI,"hex",u)
        call IssueTargetOrder(AI,"manaburn",u)
        call IssueTargetOrder(AI,"slow",u)
        call IssueTargetOrder(AI,"cripple",u)
        call IssueTargetOrder(AI,"forkedlighting",u)
        call IssueTargetOrder(AI,"antimagicshell",u)
        call IssueTargetOrder(AI,"entanglingroots",u)
        call IssueTargetOrder(AI,"purge",u)
        call IssueTargetOrder(AI,"ensnare",u)
        // --------C указанием точки--------
        call IssuePointOrder(AI,"flamestrike",x2,y2)
        call IssuePointOrder(AI,"inferno",x2,y2)
        call IssuePointOrder(AI,"shockwave",x2,y2)
        call IssuePointOrder(AI,"clusterrockets",x2,y2)
        call IssuePointOrder(AI,"impale",x2,y2)
        call IssuePointOrder(AI,"rainoffire",x2,y2)
        call IssuePointOrder(AI,"blink",x2,y2)
        call IssuePointOrder(AI,"silence",x2,y2)
        call IssuePointOrder(AI,"breathoffire",x2,y2)
        call IssuePointOrder(AI,"stasistrap",x2,y2)
        call IssuePointOrder(AI,"blizzard",x2,y2)
        // --------Без цели--------
        call IssueImmediateOrder(AI,"waterelemental" )
        call IssueImmediateOrder(AI,"windwalk" )
        call IssueImmediateOrder(AI,"thunderclap" )
        call IssueImmediateOrder(AI,"creepthunderclap" )
        call IssueImmediateOrder(AI,"spiritwolf" )
        call IssueImmediateOrder(AI,"Locustswarm" )
        call IssueImmediateOrder(AI,"Summongrizzly" )
        call IssueImmediateOrder(AI,"stomp" )
        call IssueImmediateOrder(AI,"Serpentward" )
        call IssueImmediateOrder(AI,"metamorphosis" )
        call IssueImmediateOrder(AI,"whirlwind" )
        call IssueImmediateOrder(AI,"fanofknives" )
        call IssueImmediateOrder(AI,"immolation" )
        call IssueImmediateOrder(AI,"berserk" )
        call IssueImmediateOrder(AI,"roar" )
        call IssueImmediateOrder(AI,"manashield" )
        call IssueImmediateOrder(AI,"robogoblin" )
        call IssueImmediateOrder(AI,"battleroar" )
        call RemoveLocation(Location(x2,y2))
        set x2 = 0.
        set y2 = 0.
      call GroupRemoveUnit(g,u)
      set u=FirstOfGroup(g)
      else
      call GroupRemoveUnit(g,u)
      set u=FirstOfGroup(g)
      endif
    endloop
    
   endif
   set A = A +1
 endloop
call DestroyGroup(g)
set g=null
set u=null
set AI=null
set x = 0.
set y = 0.
set x2 = 0.
set y2 = 0.
set A = 0
set B = 0
endfunction
Извиняюсь если написал не в тот раздел. Прошу помощи в поиске ошибке и её устранения.

Принятый ответ

FenikS1991, убери стоимость в 15 маны.
0
28
8 лет назад
0
ты отдаёшь 1 и тому же юниту кучу приказов до того как он успел начать исполнять предыдущий
представь если бы тебе давали противоречащие друг другу приказы
то есть просто список того что ты должен сделать прямо сейчас
не думаю что у твоего юнита есть столько различных спелов
так что используй проверку на наличие спела а так же вейты между кастами
if(GetUnitAbilityLevel(AI,'A000')>0){ // A000 это равкод спела с приказом thunderbolt
	IssueTargetOrder(AI,"thunderbolt",u);
	TriggerSleepAction(0.4);
elseif(GetUnitAbilityLevel(AI,'A001')>0) // A001 это равкод спела с приказом creepthunderbolt
	IssueTargetOrder(AI,"creepthunderbolt",u);
	TriggerSleepAction(0.4);
elseif(GetUnitAbilityLevel(AI,'A002')>0) // A002 это равкод спела с приказом banish
	IssueTargetOrder(AI,"banish",u)
	TriggerSleepAction(0.4);
}
а вообще чтобы не писать простыню кода я бы сделал бд
в бд указаны спелы которые есть у юнита, затрачиваемое мп и строка приказа
0
2
8 лет назад
0
а вообще чтобы не писать простыню кода я бы сделал бд
в бд указаны спелы которые есть у юнита, затрачиваемое мп и строка приказа
Спасибо за совет я знаю что бд отличная вещь но как юзать её в jass так и не понял...
Ошибку в карте нашёл отключив строки
call GroupRemoveUnit(g,u)
set u=FirstOfGroup(g)
в блоке else\endif. Но боты стали хуже кастовать способности, хотя теперь нет вылетов. Теперь понять бы как это дело исправить. А на будущее хотел бы попросить ещё примерчик использования бд для моего случая (для каста имеющихся способностей на героя врага), хотя-бы самый простой. Т.к этот "http://xgm.guru/p/wc3/wc3bd" пример выдаёт исключения при компиляции (говоря что есть не очищаемые переменные). а тут "http://xgm.guru/p/wc3/24007" всё ок, но как использовать не догнал.
Был бы очень благодарен.
0
28
8 лет назад
0
FenikS1991, я хз кто и что тебе выдаёт но там всё нормально работает
скачай джнгп
FenikS1991, пример того как сделать бд есть в статье что я кинул
тебе осталось лишь немного подумать
так и быть опишу тебе бд
твоё бд должно содержать строки приказов спеллов, равкоды спеллов, мп необходимое для каста спеллов
хранить экземпляры структур лучше всего в хэше по равкоду героя
при необходимости кастануть спелл ты должен доставать экземпляр структуры из хэш таблицы по равкоду твоего героя
после чего циклом проверяем наличие спелла и достаточно ли мп для его каста
если да то кастуем спелл и завершаем выполнение функции

делать за тебя тут никто не будет
если ты не можешь сам по примеру из статьи сделать то что тебе надо то тебе стоит бросить это дело и заняться вязанием (носки там или шарфик)
0
2
8 лет назад
0
FenikS1991, я хз кто и что тебе выдаёт но там всё нормально работает
скачай джнгп
Уже скачан и давно...
nvc123:
твоё бд должно содержать строки приказов спеллов, равкоды спеллов, мп необходимое для каста спеллов
хранить экземпляры структур лучше всего в хэше по равкоду героя
при необходимости кастануть спелл ты должен доставать экземпляр структуры из хэш таблицы по равкоду твоего героя
Это как раз понять и требовалось, спасибо.
nvc123:
делать за тебя тут никто не будет
И ненужно.
nvc123:
если ты не можешь сам по примеру из статьи сделать то что тебе надо то тебе стоит бросить это дело и заняться вязанием (носки там или шарфик)
Видимо ты в этом профи.
P.S Нет желанья помогать, лучше мимо прошагать.
1
29
8 лет назад
1
Знаем что такое бинарный поиск? Берем изначальный код и комментируем в нем половину строк, вылеты прекратились - половину комментариев убираем, не прекратились - комментируем половину другой половины и так пока не найдем точную причину ошибки (при шансе 50% проверять очень легко). С этого нужно было и начать и затем создавать пост.
Не уверен, что проблема именно в группе, строки эти убирать нельзя, иначе цикл иногда будет выходить бесконечным, просто обрывая поток с подвисанием.
Начни с пустого цикла по группе юнитов без приказов, выводи имя юнита на экран. Поймешь где проблема.
И вот это:
call GroupRemoveUnit(g,u)
set u=FirstOfGroup(g)
Должно все-таки быть за пределами if'а.
0
28
8 лет назад
0
Знаем что такое бинарный поиск?
ты предыдущие комменты читал?
если да то сам сможешь ответить на свой вопрос
1
29
8 лет назад
1
Ты сам ставишь свой ответ лучшим или что? Ты вообще проверял своё решение?
1
28
8 лет назад
1
кстати у меня вопрос
зачем эта строка
call RemoveLocation(Location(x2,y2))
Doc, если бы ты прочёл все предыдущее комменты то понял бы что проверял
Doc, и судя по тому что у него 2 вложенных цикла + простыня кода там может наступать лимит потока
+ лог какой то левый
имхо то что фатал вызван следующим кодом это бред
call GroupRemoveUnit(g,u)
set u=FirstOfGroup(g)
0
2
8 лет назад
0
Ты сам ставишь свой ответ лучшим или что? Ты вообще проверял своё решение?
но я точно не ставлю. Пока что.
Doc:
Знаем что такое бинарный поиск?
знаем.~Doc:
Не уверен, что проблема именно в группе
Да я уже тоже не уверен. Даже не уверен что именно в этой функции. Doc:
И вот это:
call GroupRemoveUnit(g,u)
set u=FirstOfGroup(g)
Должно все-таки быть за пределами if'а
Учту. Исправлю.
nvc123:
имхо то что фатал вызван следующим кодом это бред
Тут я тоже согласен. И видимо что вылеты прекратились это просто совпадение, ведь карта вылетает как я уже говорил не всегда, а пару сыгранных игр по 1.2 часа (для проверки) могли просто не дать результата. Закоментировал эти строчки я только потому что был не уверен что правильно работаю с группой либо циклом. Т.к уж извините но мне ещё сложно вникнуть в этот язык хоть и статейки тут читал на форуме. До этого я плотно работал с VB.NET, VB 6.0, и чуть менее C#. Поэтому объявляя переменные в jass по привычке использую синтаксис
VB.NET.)) Самому смешно.
nvc123:
+ лог какой то левый
Лог предоставил по средствам программы найденной тут, когда копался в ресурсах на xgm. Ну как я уже понял это не то что требуется.
Строчки разкоментировал и продолжил тестить. Теперь при вылетах лог обрывается всё чаще и чаще на строчках curCol и numCols. А эти строчки - переменные, функции MultiboardSetItemValueBJ()
Тут я начал грешить на свой мультиборд. Но пока ни к чему не пришёл, да и кто знает, может программа которая пишет лог сама как то некорректно работает. А может быть ошибка не одна а парочка.
Ужас, ищу ошибку уже более двух недель, за это время проверил каждого героя по отдельности, проверил все их нестандартные способности, проверил все предметы способности которых тоже нестандартные, всё работает идеально на разных целях (на героях, иллюзиях, юнитах и т.д) Устал биться, поэтому создал пост, в надежде что лог не врёт а гуру этого языка смогут определить ошибку на глаз (которую я так и ненашёл).
Моя последняя надежда на то что ошибка в мультиборде (если так то ужас сколько всего переделывать там), но пятой точкой чую что отключив этот триггер, ничего не изменится. (Хотя MultiboardSetItemValueBJ() только в нём)
0
2
8 лет назад
0
Если ктото ещё читает эту тему (прошу прощения что наверное задолбал уже),но функцию я полностью переписал, и теперь в ней даже нет цикла в цикле, но вылеты продолжились.
Вообщем улыбнулась мне удача и как раз перед вылетом я случайно сохранил игру. Потом много раз загружал игру и тестил, искал причину.
Вообщем имеется босс (нейтрально враждебный, его способности баш, мана выжигалка пассивная, и криты.)
Вылет происходил во время битвы с боссом одного из ботов (точнее одно из типов героев,ботов), отправлял их по одному к нему и все норм а именно этот даёт вылет.
Думал в чём причина, и увидел одну закономерность.
босс бьёт по герою и за несколько ударов выжигает ему всю ману, критует и станит. Как только у героя заканчивается мана игра вылетает, с другими всё нормально видимо потому что они не собирают прелмет пополняющий ману, а этот герой собирает этот предмет.
В тригерах я этого не задавал, но видимо герой пытается пополнить ману нажав на предмет, а маны для использования не хватает. и игра вылетает (я так полагаю). Как тогда бороться с этой проблемой? ведь в тригерах я не задавал поведения боту при битве с крипами и вобще что нужно пользоваться предметами независимо с крипами или героями.
Если кто сможет сказать что да как то я даже могу выложить саму карту и сохранённую игру где бот идёт на босса и происходит вылет.
вот вам типичный пример "
Создал тестовую карту на неё поместил 2 стандартных героя. дал им абилку выжигающюю ману "Магический огонь" (выжигает всю ману сразу.) создал 1 предмет (пополняющий ману за 15 маны) дал предмет герою врага. Обсолютно никаких тригерров нет.
Выжигаешь ману у героя компа и игра вылетает.
Загруженные файлы
1
21
8 лет назад
Отредактирован Sozidar
1
FenikS1991, убери стоимость в 15 маны.
Принятый ответ
0
2
8 лет назад
0
TripleKor:
FenikS1991, убери стоимость в 15 маны.
да я убрал. Только всё равно интересно почему вылетает то? я изза этой ерунды всю карту по 150 раз перерыл, все bj нативками заменил кучу функций переписал.. а тут вон оно что
и ещё 1 вопросик. ещё один глюк нашёлся странный. имеется герой, для него есть улучшение, каждый уровень улучшения добавляет 5 маны 5 hp и 3 атаки для героев. 100 уровней улучшений. Для всех героев работает нормально. Для одного героя вот такая проблема:
Герой имеет абилку стандартную, создаёт иллюзии при использовании. Так вот когда улучшение доходит до 31 уровня.. герой больше не создаёт иллюзии. они пропадают до того как успевают появиться...
PS это уже третий необъяснимый глюк найденный в Warcraft (
В принципе фиг с этим, снизил улучшения до 30 уровней и всё норм. тему можно закрывать все спасибо за помощь.
0
28
8 лет назад
0
все bj нативками заменил кучу функций переписал..
это как бы хорошо
Чтобы оставить комментарий, пожалуйста, войдите на сайт.