•

# SimulationCraft for Rogues

268 replies to this topic

### #1 dedmonwakeen

dedmonwakeen

Bald Bull

• Members
• 1,302 posts

Posted 14 January 2009 - 07:37 PM

Recent Rogue Changes
• Not Yet Implemented
• None that we know of....
• Code Updated
• Released
• Deadly Poison proc on 5-stack triggers poison on other weapon
• Tier 10 set bonuses

Simulation Output

The PTR SampleOutput is just T9 BiS with T9 set bonuses replaced with T10 set bonuses.

http://simulationcra...ule Source Code

Help Needed:
I am able to keep the core module up to date with recent Rogue mechanic changes (or discoveries). However, I need help maintaining the set of default profiles which include gear, talents, glyphs, and action priority lists. Please contact me if you can help out.

### #2 sp00n

sp00n

Bald Bull

• Members
• 1,836 posts

Posted 14 January 2009 - 08:47 PM

Was looking through your code and searched for those FIXME!s. Tried to answer them to the best of my knowledge.

trigger_relentless_strikes( this ); // FIXME! Does this happen even if you miss?

I know it used to, at least for "immune" type misses. Not sure whether it still does though.
Going to check on a training dummy.
// EDIT
Nope, no 25 energy on a parried/missed eviscerate.

1[/hr]

// FIXME! Do these poisons benefit from spell-power?
// FIXME! Is it necessary to perform a spell-hit roll?
// FIXME! Can this ability crit? Are the crits +100% or +50%?
// FIXME! Perhaps better to model this as a spell......
may_miss = may_dodge = may_parry = may_glance = may_block = false;

Deadly Poison scales with attack power, I see no interaction with spell power. Would be a moot point anyway imho.
As for spell hit roll, Deadly Poison can be fully resisted on its application (a proc), and partially resisted on each tick.
Instant and Wound Poison can both miss and be partially resisted.

Deadly Poison cannot crit, but Instant and Wound can. The base damage is 150%, but there are quite some modifyers, so here's the formula from Vulajin's spreadsheet:
Crit Bonus = 1.5 * (1+0.03*red) * (1+0.02*tmurder*OR(btype="Humanoid",btype="Beast",btype="Dragonkin",btype="Giant")) * (1+0.05*AND(crace="Troll",btype="Beast")) * (1+0.04*tprey)-1
My current modifyer as a combat Night Elf rogue is 185.40% percent according to this formula.

1[/hr]

base_tick_time = 0.5; // FIXME! Are the frequency of attacks affected by haste?

According to my latest combat log they aren't. 0.5 seconds between each set of attack, at least as far as combat log accuracy goes.

1[/hr]

if( result_is_hit() ) // FIXME! Does OH swing if MH misses?

For Killing Spree, no idea. Looking through varios WWS reports, I don't see a single miss or even dodge/parry on Killing Spree. It seems its only outcome is a hit/crit, or failed swings simply don't register in the combat log.
For Mutilate, both Swings share a miss/dodge/parry outcome, but have an independant crit chance. I.e. if MH misses, OH doesn't even register in the combat log.

// EDIT
Checked on a training dummy as well. Killing Spree can miss, and if it does, neither hand lands an attack, similar to Mutilate. Wasn't able to determine if it can be dodged though (Surprise Attacks?).

1[/hr]

trigger_gcd = 0; // FIXME! Does this ability trigger the GCD?

*shrug* A comment on WoWHead says no, but that's from 2007. No idea. Haven't been playing much around with Shadowstep.

1[/hr]

// FIXME! These are level 70 values.
attribute_base[ ATTR_STRENGTH ] = 94;
attribute_base[ ATTR_AGILITY ] = 156;
attribute_base[ ATTR_STAMINA ] = 90;
attribute_base[ ATTR_INTELLECT ] = 37;
attribute_base[ ATTR_SPIRIT ] = 65;

Shameless copy again from Vulajin:

Race|Strength|Agility|Stamina
Blood Elf|110|191|103
Dwarf|115|185|108
Gnome|108|192|104
Human|113|189|105
Night Elf|110|194|104
Orc|116|186|107
Troll|114|191|106

Stopped Playing

### #3 dedmonwakeen

dedmonwakeen

Bald Bull

• Members
• 1,302 posts

Posted 14 January 2009 - 09:56 PM

Thanks to sp00n, latito, lade, and tinwhisker for their feedback.

Support for poisons was completely overhauled. I'm happy with the result.

I believe I have cleared up all the "FIXME" statements. Of course, that just removes the problems I know about. Heh.

The link posted in the OP will show the updated code.

I'll begin pipe-cleaner testing shortly.

### #4 drumbum

drumbum

King Hippo

• Members
• 500 posts

Posted 15 January 2009 - 03:03 AM

It appears that you did not implement the highest rank of Instant Poison: . I imagine it was because roman numerals don't play nicely when items are listed alphabetically, such as when searching for it on Wowhead.

In any case, the tooltips for all versions of Instant Poison are wrong anyway. The correct damage ranges for all relevant versions of IP to this project are as follows:

Instant Poison IX (level 79) --> 300-400 damage (average 350)
Instant Poison VIII (level 73) --> 245-327 damage (average 286)
Instant Poison VII (level 68) --> 161-215 (average 188)
Instant Poison VI (level 60) --> 76-100 (average 88)

These values can be found from the spell details of the relevant spells associated with each poison, e.g., Instant Poison IX.

Edit: You're also missing ! (It deals 74 base damage per 3 seconds per stack.)

### #5 dedmonwakeen

dedmonwakeen

Bald Bull

• Members
• 1,302 posts

Posted 15 January 2009 - 03:34 AM

It appears that you did not implement the highest rank of Instant Poison: . I imagine it was because roman numerals don't play nicely when items are listed alphabetically, such as when searching for it on Wowhead.

Edit: You're also missing ! (It deals 74 base damage per 3 seconds per stack.)

Thanks! I've committed the fixes for the poisons. Link in OP should be up-to-date.

### #6 dedmonwakeen

dedmonwakeen

Bald Bull

• Members
• 1,302 posts

Posted 15 January 2009 - 04:33 AM

I want to make sure I have a reasonably comprehensive set of Rogue profiles in the default raid config.

Finding the various "interesting" talent builds is not difficult given the wealth of information on these forums. The hard part is creating the action priority list.

At present SimulationCraft only supports a single action priority list. The sometimes complex flow charts of player actions need to be distilled into a single priority list which can be challenging.....

I've already gotten some useful information in this area through email and PMs, but I decided to post a request here as well:

If some experienced Rogues can post their own (or known-to-be-effective) "flow charts" and accompanied talent link I would be most appreciative. Please attempt to condense the decision making into a single priority list. Assume that each action has access to whatever conditional information it needs to properly evaluate its ready state.

Essentially, it is a sequence of "action" and "conditional expression" pairs:

Action1, Expression1
Action2, Expression2
etc

Please include abilities with long cooldowns and if opening the fight in stealth is a reasonable option. please illustrate that in the action list.

### #7 chalon

chalon

Founder of the Chalonverse

• Members
• 1,717 posts

Posted 15 January 2009 - 07:47 AM

Well, I'm not going to type it out in the syntax, but I'll try to explain the optimal cycle for standard raid Mutilate assuming a single target - Talent Calculator - World of Warcraft .

Engage
1. Always open from stealth (this is possible on the vast majority of the fights)
2. Pre-stack HfB before the pull occurs, while you are in stealth. Do this ~2s before the pull occurs, so you're at full energy and 28s remaining on HfB when you engage.
3. Your start sequence should be: Mutilate, Mutilate, SnD

Main Cycle Priority
This is basically what you would use to determine what you should do next. So basically, check if the conditions for item #1 are met. If they are, do that for now. If they aren't, check if item #2 are met, so on and so forth.

1. If HfB is at <2s remaining, refresh it
2. If Slice and Dice is at <2s remaining, Envenom to refresh it
3. If <4 combo points, Mutilate
4. If you have >= 4 combo points and Rupture is not up on the target, Rupture
5. If you have >= 4 combo points, Envenom. If Cold Blood is up, you are going to use it right before the Envenom

I don't know how to particularly fit these in, as sometimes they're judgement calls. If you get the above working it should be fairly accurate, but the following are things which you may sometimes do in actual play.

Rupture Clipping - You can only overwrite a Rupture if your current AP is >= the AP you had when the Rupture was previously applied AND if the remaining duration on the Rupture is less than whatever time the Rupture would be if you applied it right now. So what this means is effectively, the only time you will overwrite a Rupture is if the Rupture duration is dwindling down, but so are the duration of +AP procs (such as Berserking, Mirror of Truth, Darkmoon Card: Greatness). So for example, lets say you have 4 CPs, 2s left on Berserking, and Rupture at 4s remaining. It probably makes sense in this instance to clip that Rupture, provided it's not at a cost of the higher priority HfB and SnD.

Energy Pooling - There are some non fight-specific considerations for when you should or shouldn't energy pool. Never pool energy if it's going to cost you HfB or SnD. And of course, you don't want to pool energy if you are close to capping out. However, pool energy if:
1. You have plenty of time remaining on SnD and HfB, and Rupture is about to fade. Save energy until Rupture fades and then Rupture.
2. If you have 4 CPs, and 4 stacks of DP on the target, it may make sense to pool energy until you get to 5 stacks, and Envenom at that point -- because this will mean that you don't drop to 0 stacks of DP when you Envenom.
3. You are also going to pool if you are going to execute a Vanish/Overkill (outlined below)

Vanish/Overkill - You should generally wait until some point further in the cycle to do this. But basically, what you do is Vanish and immediately execute either a finisher or a Mutilate. This won't interrupt your white attacks if you do it properly, but will get you 6 seconds of -10 energy off each move you perform. So the idea would be to pool up as much energy as feasible to take maximum advantage of the Overkill buff.

Tricks of the Trade - If you are buffing someone else with it, you are just going to use it every time the cooldown is up, provided you aren't messing up your cycle.

That should basically cover most of what you'd need to get a fairly accurate model for Mutilate running. There's a lot of fight-specific stuff, but I gather simulation craft really only cares about 100% ToT fights basically, so that shouldn't be a problem.

By the way, I just skimmed your code, and I'm not quite sure if your Mutilate calculation is correct for the off-hand. The MH is of course 181 + (MH weapon damage). However, the OH is 181 * (1 + 0.1 * dual_wield_spec) + (OH weapon damage) * 0.5 * (1 + 0.1 * dual_wield_spec). From looking at it I'm not sure if you've got the multiplier correctly applied to that 181. But to be honest the code is a bit difficult to follow in that regard.

### #8 dedmonwakeen

dedmonwakeen

Bald Bull

• Members
• 1,302 posts

Posted 15 January 2009 - 08:38 AM

By the way, I just skimmed your code, and I'm not quite sure if your Mutilate calculation is correct for the off-hand. The MH is of course 181 + (MH weapon damage). However, the OH is 181 * (1 + 0.1 * dual_wield_spec) + (OH weapon damage) * 0.5 * (1 + 0.1 * dual_wield_spec). From looking at it I'm not sure if you've got the multiplier correctly applied to that 181. But to be honest the code is a bit difficult to follow in that regard.

Thanks for the great detail!

In response to your last question, I believe there is an error in my code because I apply the 50% off-hand reduction to the entire damage calculation ( bonus_dmg + weapon_dmg ) instead of just the weapon_dmg portion. I'll fix this ASAP.

The high-level mechanics for an "action" are defined here: http://simulationcra...k/sc_action.cpp

If you start from execute() you get a good picture of the default mechanics of an "action" in simulationcraft.

There are three sets of variables that affect the outcome of an action:
(1) base_xxx : These vars are set just once during initialization
(2) player_xxx: These vars are set in the player_buff() methods and represent the dynamic state of the player
(3) target_xxx: These vars set set in the target_debuff() methods and represent the dynamic state of the target

Chance to crit is: base_crit + player_crit + target_crit
Total power is: base_power + player_power + target_power
Total damage multiplier is: base_multiplier * player_multiplier * target_multiplier
etc

EDIT: The fix to the 50% off-hand reduction has been checked in.

### #9 drumbum

drumbum

King Hippo

• Members
• 500 posts

Posted 15 January 2009 - 03:52 PM

The way you are calculating the crit factor seems to be incorrect. I believe you are adding the multipliers when they should be getting multiplied together. Also, Lethality works even more strangely since it does not increase critical strike damage but instead it increases critical strike damage bonus. I will elaborate on this in this post.

Let $x$ be the amount of damage dealt with a non-crit attack, and $b$ be the bonus crit multiplier, such that the damage dealt by a crit is always $x\times(1+b)$. I am using this definition because I *believe* that $b$ should be equal to the variable base_crit_bonus used in the code. (If this is not the way this variable is used, let me know and I can update my post to match.)

If you imagine a non-crit attack deals $x$ damage, then a regular crit (ignoring any modifiers for the moment) would deal $2x$ damage. The bonus damage (i.e., the difference in damage between a crit and hit) is equal to $2x-x=x$. Therefore, 30% of $x$, or $0.3x$, is added to the crit damage. In this scenario, $b=1.3$ and the crit deals $x\times(1+1.3)=2.3x$ damage total.

If that was the only concern, it wouldn't be too bad, but it also interacts in a perhaps unintuitive way with modifiers that multiply directly with the crit factor. To demonstrate, let's introduce RED into the equation:

With RED, a crit would deal $2x\times1.03=2.06x$ damage. However since hits still deal $x$ damage, the bonus damage is now equal to $2.06x-x=1.06x$, so $b=1.06$ (without Lethality). Lethality increases this value by 30%, giving us $b=1.06\times1.3=1.378$.

As far as I know, all of the abilities that modify crit damage are calculated before Lethality is added in. So, if we have 5/5 Lethality, RED, and 2/2 Murder all at the same time, $b=(2\times1.03\times1.04-1)\times1.3$.

By the way, if you are wondering why I included Murder in the crit factor calculation, it's because Murder has (for whatever reason) always had a second effect of increasing crit damage by the same amount, even though it isn't indicated on the tool tip. This means crits get to sort of "double-dip" into the talent.

So, now, assuming you are adding all of the crit multipliers one at a time, it's important that you treat the multipliers like so:

base_crit_bonus = (base_crit_bonus + 1.0) * (1.0 + p -> talents.prey_on_the_weak * 0.04) * (1.0 + p -> talents.murder * 0.02) - 1.0;

The lone exception is Lethality, which seems to be fine the way you already have it:

base_crit_bonus *= 1.0 + p -> talents.lethality * 0.06;

An important caveat though is that Lethality *must* be calculated last, or the value will be wrong.

### #10 Tinwhisker

Tinwhisker

Bald Bull

• Members
• 1,032 posts

Posted 15 January 2009 - 09:10 PM

If you have an ability like Cold Blood that does not trigger the GCD, does the program fire that action and them step through the priority list again? (I'm assuming it does.)

Reason being, if you are at a point where you will be performing a 5CP Envenom you should fire off Cold Blood first if available.

Also, is there an "expirations_rupture" that can be used to check rupture duration on the target? Or a way to reference Deadly Poison stack count? Fairly certain they're in there and I'm mangling what I think the names should be.

### #11 dedmonwakeen

dedmonwakeen

Bald Bull

• Members
• 1,302 posts

Posted 15 January 2009 - 10:14 PM

If you have an ability like Cold Blood that does not trigger the GCD, does the program fire that action and them step through the priority list again? (I'm assuming it does.)

Reason being, if you are at a point where you will be performing a 5CP Envenom you should fire off Cold Blood first if available.

Also, is there an "expirations_rupture" that can be used to check rupture duration on the target? Or a way to reference Deadly Poison stack count? Fairly certain they're in there and I'm mangling what I think the names should be.

Most abilities that do not trigger the GCD are single actions in the priority list and your assumption is correct about the priority list being stepped through again. There are some exceptions such as the Mage skill "Presence of Mind" in which you are REALLY trying to pair two abilities. There are different ways that they can be paired: The cold_blood action could have conditionals that prevent it from firing until the secondary action Envenom is ready. Alternatively, we could go the PoM route and make cold_blood take a secondary action as part of its options: .../cold_blood,envenom,min_combo_points=5/...

This is no "expirations_rupture" right now, but each action has a "duration_ready" field which gets set during execute() if there is a DoT component. When other player classes have needed access to ticking DoTs, I've created "active_xxx" fields in the main class structure to provide a portal into all the information regarding the ticking DoT. In this case, using it would look something like:

rupture_expires = p -> active_rupture -> duration_ready - sim -> current_time;

The Deadly Poison stack count can be accessed via:

### #12 dedmonwakeen

dedmonwakeen

Bald Bull

• Members
• 1,302 posts

Posted 16 January 2009 - 02:29 AM

The way you are calculating the crit factor seems to be incorrect. I believe you are adding the multipliers when they should be getting multiplied together. Also, Lethality works even more strangely since it does not increase critical strike damage but instead it increases critical strike damage bonus. I will elaborate on this in this post.

Thanks again for the time taken to provide such great detail, especially regarding the mechanics of Murder which I never would have known about without your help.

SimulationCraft does indeed distinguish between "critical damage modifiers" and "critical damage BONUS modifiers".

My understanding of the mechanics is as follows:

crit_damage = normal_damage * ( 1.0 + crit_bonus )

Spell: crit_bonus = 0.5
Attack: crit_bonus = 1.0

The standard equation I've seen used throughout EJ is of the form:

crit_bonus = ( ( 1.0 + crit_bonus ) * ( 1.0 + crit_damage_mod ) - 1.0 ) * ( 1.0 + crit_damage_BONUS_mod )

As you point out, there may be multiple "damage_mods" and "damage_BONUS_mods" and it is important that they get combined in the right order.

In traditional spreadsheet applications, every spell/attack is usually coded to understand each and every talent, buff, debuff, and passive item effect that modifies it. Given the scope of SimulationCraft I simply could not do that. The chance for error and the difficulty it posed to maintenance made it impossible. Instead I implemented a hierarchy of modifiers:

1: mods specific to a spell/attack
2a: mods applied to all spells of a class
2b: mods applied to all attacks of a class
3a: mods applied to all spells
3b: mods applied to all attacks
4: mods applied to all actions (spells + attacks)

Unfortunately, this makes it quite difficult to model "critical damage modifiers" because of their order dependency. (The beta version of the Shaman Elemental Oath was particularly painful because it represented a dynamic critical damage modifier that forced me to defer a great deal of calculation.)

I decided to revisit the crit_bonus formula to see if there was an alternative expression that gave me more freedom in how it was combined, while still staying within the statistical margins used to confirm the original formulation. With the exception of passive talents, which first stack additively, all crit bonus modifiers are designed to stack multiplicatively. Essentially, this means that "critical damage modifiers" need to be translated into "critical damage BONUS modifiers".

This is the model that I use:

Spells:
crit_bonus = 0.5
crit_bonus *= ( 1.0 + 3 * crit_damage_mod_1 )
crit_bonus *= ( 1.0 + 3 * crit_damage_mod_2 )
etc...
crit_bonus *= ( 1.0 + crit_damage_BONUS_mod_1 )
crit_bonus *= ( 1.0 + crit_damage_BONUS_mod_2 )
etc...
crit_bonus *= ( 1.0 + ( passive_talent_crit_damage_BONUS_mod_1 + passive_talent_crit_damage_BONUS_mod_1 + ... ) )

Attacks:
crit_bonus = 1.0
crit_bonus *= ( 1.0 + 2 * crit_damage_mod_1 )
crit_bonus *= ( 1.0 + 2 * crit_damage_mod_2 )
etc...
crit_bonus *= ( 1.0 + crit_damage_BONUS_mod_1 )
crit_bonus *= ( 1.0 + crit_damage_BONUS_mod_2 )
etc...
crit_bonus *= ( 1.0 + ( passive_talent_crit_damage_BONUS_mod_1 + passive_talent_crit_damage_BONUS_mod_1 + ... ) )

For example.....
A 3% mod on total spell critical strike damage is equivalent to a 9% mod on just the critical damage portion.
A 3% mod on total attack critical strike damage is equivalent to a 6% mod on just the critical damage portion.

With this formulation, the only part that is absolutely necessary to include in the spell/attack initialization is the contribution from passive talents.

Specifically, the code initializes the following variables:
base_crit_bonus = 0.5 or 1.0 depending upon spell/attack
player_crit_bonus = 1.0
target_crit_bonus = 1.0

These are combined when an action is executed: base_crit_bonus * player_crit_bonus * target_crit_bonus
The base_crit_bonus is modified during initialization to model talents.
The player_crit_bonus is used to model the meta gems at steps 3a and 3b in the list above.

The degenerative forms of these equations, in which there is only one (or zero) "crit_damage_mod", will match exactly the formula at the top of this post. It starts to diverge when two or more "crit_damage_mod" variables come into play, as is the case apparently with RED and Murder. However, the difference in this case is quite small and well within a reasonable margin of error.

Are there any contant damage attacks that can be used to 100% confirm the way in which multiple "crit_damage_mod" variables are combined? If we are forced to rely upon min/max ranges of critical strike damage, then it is likely that both models will always fit the data since the differences are so small......

I'm certainly open to change, but sometimes I am forced to make minor modeling compromises (as all TC does) in order to reduce complexity. Sometimes that complexity is of a runtime nature and sometimes that complexity is of an engineering nature......

### #13 drumbum

drumbum

King Hippo

• Members
• 500 posts

Posted 16 January 2009 - 05:14 AM

Gouge deals a constant amount of damage (as long as attack power is constant) and would probably be useful for this sort of testing. If I find the time I'll try to confirm my statements above via in-game testing. This was originally tested and confirmed at some point early in Burning Crusade by someone on this forum, but I'd probably have to dig to find the exact posts.

### #14 dedmonwakeen

dedmonwakeen

Bald Bull

• Members
• 1,302 posts

Posted 16 January 2009 - 06:16 AM

Gouge deals a constant amount of damage (as long as attack power is constant) and would probably be useful for this sort of testing. If I find the time I'll try to confirm my statements above via in-game testing. This was originally tested and confirmed at some point early in Burning Crusade by someone on this forum, but I'd probably have to dig to find the exact posts.

That would be perfect. All I could find here (and elsewhere) were min/max tests which were helpful..... but not conclusive..... Or they used fixed damage abilities and only one crit damage modifier. An experiment with both RED and Prey on the Weak would be perfect. The mismatch between Murder's tooltip and the behaviour you report makes me inclined to take that out of the experiment if possible.

### #15 Vulajin

Vulajin

Vula'jin the Void, blessed by the loa

• Moderators
• 5,924 posts

Posted 16 January 2009 - 08:42 AM

http://elitistjerks....5-post1746.html

This is a "min-max" test but it's reasonably conclusive. Also, the following is from a post I typed up to prove an entirely different point during open beta:

Test parameters: I took a 2.6 speed weapon with a damage range of 2-4, using a gear setup with 2014 AP. Average expected damage per swing:

- On an elemental: 377
- On a humanoid: 385 (2/2 Murder)
- On a beast: 404 (2/2 Murder and Troll Beast Slaying)

I observed critical damage values of the following (as examples) with 0/5 Prey on the Weak:

- On an elemental: 773
- On a humanoid: 809
- On a beast: 890

I observed critical damage values of the following (as examples) with 5/5 Prey on the Weak:

- On an elemental: 970
- On a humanoid: 1009
- On a beast: 1116

Now, an interesting thing that I discovered doing this test is that Troll Beast Slaying, like Murder, provides both 5% increased damage against beasts and also 5% increased critical strike damage against beasts. So the crit multipliers before Prey on the Weak, for each type of mob, are:

- Elemental: 2 * 1.03 (RED) = 2.06
- Humanoid: 2 * 1.03 (RED) * 1.02 (Murder) = 2.10
- Beast: 2 * 1.03 (RED) * 1.02 (Murder) * 1.05 (Beast Slaying) = 2.21

If Prey on the Weak stacks as "increased critical strike damage" (i.e. the same as RED, Murder, and Beast Slaying), our crit multipliers should become:

- Elemental: 2.06 * 1.25 = 2.58
- Humanoid: 2.10 * 1.25 = 2.63
- Beast: 2.21 * 1.25 = 2.76

If Prey on the Weak stacks as "increased critical strike damage bonus" (i.e. the same as Lethality), our crit multipliers should become:

- Elemental: (2.06 - 1) * 1.25 + 1 = 2.33
- Humanoid: (2.10 - 1) * 1.25 + 1 = 2.38
- Beast: (2.21 - 1) * 1.25 + 1 = 2.51

Looking at the damage numbers I experienced, they're all in line with the first way of calculating it, where Prey on the Weak stacks like RED/Murder/Beast Slaying rather than like Lethality. This makes it very strong, especially because it's applying to all attacks right now, not just white. My current model puts it at an overall ~16% DPS increase for 5 talent points assuming ~40% raid-buffed crit (using my current gear at level 70).

If we assume that Prey on the Weak applying to non-white attacks is an error, then it becomes an overall ~11% DPS increase for 5 talent points assuming the same crit levels.

In either case this single talent is probably enough to put Mutilate in combat's dust, unless there are some serious buffs to the various Assassination talents.

Ignoring the parts about Prey on the Weak, let's look at what the multipliers would have been if "increased crit damage" effects stacked additively rather than multiplicatively (read each as "no Prey on the Weak / Prey on the Weak"):

- Elemental: 2 * 1.03 = 2.06 / 2 * (1 + 0.03 + 0.25) = 2.56
- Humanoid: 2 * (1 + 0.03 + 0.02) = 2.10 / 2 * (1 + 0.03 + 0.02 + 0.25) = 2.60
- Beast: 2 * (1 + 0.03 + 0.02 + 0.05) = 2.20 / 2 * (1 + 0.03 + 0.02 + 0.05 + 0.25) = 2.70

Given these multipliers, I would've expected my crits to deal:

- Elemental: 777 / 965
- Humanoid: 808 / 1000
- Beast: 889 / 1090

Note that, given my numbers quoted above, the damage I actually dealt with all four modifiers was significantly greater than that we'd expect if the modifiers were additive. As a result, the modifiers almost certainly must be multiplicative.

Yep, still a fucking idiot.

### #16 dedmonwakeen

dedmonwakeen

Bald Bull

• Members
• 1,302 posts

Posted 16 January 2009 - 01:32 PM

Thanks, Vulajin. That was very very helpful, because it showed quite clearly two things:

(1) My model is unacceptable. Once we have RED+Prey+Murder all stacking, the difference between my model and your data is just too large.

(2) The model for critical strike damage calculation is consistent which means I can model this conveniently without making my code look like spaghetti.

You have shown that the modifiers that affect total critical strike damage are multiplicative. Mechanics for several caster classes have shown that passive talent modifiers that affect the critical strike damage BONUS stack additively.

If I drop my obsession with modeling this with just one variable, then the code cleans up nicely. For each action, I will build up spearate "crit_multiplier" and "crit_bonus" values.

I'll get this checked in today. Again, I must say I really really appreciate the level of detail people have provided.

### #17 dedmonwakeen

dedmonwakeen

Bald Bull

• Members
• 1,302 posts

Posted 16 January 2009 - 07:52 PM

I've changed the simulationcraft architecture to support the modeling mechanics I've learned in this thread.

action_t has a new method:
double action_t::total_crit_bonus()
{
double crit_multiplier = (   base_crit_multiplier *
player_crit_multiplier *
target_crit_multiplier );

double crit_bonus_multiplier = (   base_crit_bonus_multiplier *
player_crit_bonus_multiplier *
target_crit_bonus_multiplier );

double crit_bonus = ( ( 1.0 + base_crit_bonus ) * crit_multiplier - 1.0 ) * crit_bonus_multiplier;

return crit_bonus;
}


The Rogue module sets "base_crit_multiplier", "player_crit_multiplier", and "base_crit_bonus_multiplier" as needed.

I'll start testing the basic cycles this weekend.

### #18 PessimiStick

PessimiStick

Piston Honda

• Members
• 160 posts

Posted 16 January 2009 - 09:09 PM

Browsing through the module code from the OP, noticed the following:

For Rupture:
base_multiplier *= 1.0 + ( p -> talents.blood_spatter * 0.15 +
p -> talents.find_weakness * 0.02 +
p -> talents.serrated_blades * 0.10 );

This should be 0.03 -- Find Weakness is actually 3% per point on DoTs, for reasons unknown.

Edit: http://elitistjerks...._mechanics/p11/ Posts 255, 256, and 257 for the math.
Also Find Weakness - Spell - World of Warcraft Effect #2.

### #19 drumbum

drumbum

King Hippo

• Members
• 500 posts

Posted 16 January 2009 - 09:46 PM

Just noting a few issues I discovered while scanning through your code:

1) Improved Poisons (talent) seems to be increasing spell hit chance with poisons for some reason.

2) The proc chance of Relentless Strikes depends on the number of combo points consumed by the finisher. (Currently appears to be ignoring number of combo points.) The chance to proc should always be $0.04 \times c \times t$ where $c$ is the number of combo points consumed and $t$ is the number of talent points in Relentless Strikes.

3) Your comment in the Seal Fate code mentions auto attack. Rest assured that auto attacks cannot proc Seal Fate (only abilities that add combo points can). No bug here -- but just wanted to clear that up in case there was confusion.

### #20 dedmonwakeen

dedmonwakeen

Bald Bull

• Members
• 1,302 posts

Posted 16 January 2009 - 09:58 PM

Browsing through the module code from the OP, noticed the following:

For Rupture:
base_multiplier *= 1.0 + ( p -> talents.blood_spatter * 0.15 +
p -> talents.find_weakness * 0.02 +
p -> talents.serrated_blades * 0.10 );

This should be 0.03 -- Find Weakness is actually 3% per point on DoTs, for reasons unknown.

Edit: http://elitistjerks...._mechanics/p11/ Posts 255, 256, and 257 for the math.
Also Find Weakness - Spell - World of Warcraft Effect #2.

Fixed and committed..... and thanks for that "buggy" link! I'll examine it in detail later tonight.

Just noting a few issues I discovered while scanning through your code:

1) Improved Poisons (talent) seems to be increasing spell hit chance with poisons for some reason.

2) The proc chance of Relentless Strikes depends on the number of combo points consumed by the finisher. (Currently appears to be ignoring number of combo points.) The chance to proc should always be $0.04 \times c \times t$ where $c$ is the number of combo points consumed and $t$ is the number of talent points in Relentless Strikes.

3) Your comment in the Seal Fate code mentions auto attack. Rest assured that auto attacks cannot proc Seal Fate (only abilities that add combo points can). No bug here -- but just wanted to clear that up in case there was confusion.

1) I wasn't exactly sure how Improved Poisons worked, so I added it both to the proc chance and the spell hit. Fix committed.

2) Thanks for that catch! Fix committed.

3) Brain-fart on my part. Comment changed to reduce confusion.

Link in OP should be up-to-date.

#### 0 user(s) are reading this topic

0 members, 0 guests, 0 anonymous users