Menu Search
Jump to the content X X
SmashingConf London Avatar

We use ad-blockers as well, you know. We gotta keep those servers running though. Did you know that we publish useful books and run friendly conferences — crafted for pros like yourself? E.g. our upcoming SmashingConf London, dedicated to all things web performance.

CSS Specificity And Inheritance

CSS’ barrier to entry is extremely low, mainly due to the nature of its syntax. Being clear and easy to understand, the syntax makes sense even to the inexperienced Web designer. It’s so simple, in fact, that you could style a simple CSS-based website within a few hours of learning it. [Links checked March/06/2017]

But this apparent simplicity is deceitful. If after a few hours of work, your perfectly crafted website looks great in Safari, all hell might break loose if you haven’t taken the necessary measures to make it work in Internet Explorer. In a panic, you add hacks and filters where only a few tweaks or a different approach might do. Knowing how to deal with these issues comes with experience, with trial and error and with failing massively and then learning the correct way.

Understanding a few often overlooked concepts is also important. The concepts may be hard to grasp and look boring at first, but understanding them and knowing how to take advantage of them is important.

Further Reading on SmashingMag: Link

Two of these concepts are specificity and inheritance. Not very common words among Web designers, are they? Talking about border-radius and text-shadow is a lot more fun; but specificity and inheritance are fundamental concepts that any person who wants to be good at CSS should understand. They will help you create clean, maintainable and flexible style sheets. Let’s look at what they mean and how they work.

The notion of a “cascade” is at the heart of CSS (just look at its name). It ultimately determines which properties will modify a given element. The cascade is tied to three main concepts: importance, specificity and source order. The cascade follows these three steps to determine which properties to assign to an element. By the end of this process, the cascade has assigned a weight to each rule, and this weight determines which rule takes precedence, when more than one applies.

1. Importance Link

Style sheets can have a few different sources:

  1. User agent
    For example, the browser’s default style sheet.
  2. User
    Such as the user’s browser options.
  3. Author
    This is the CSS provided by the page (whether inline, embedded or external)

By default, this is the order in which the different sources are processed, so the author’s rules will override those of the user and user agent, and so on.

There is also the !important declaration to consider in the cascade. This declaration is used to balance the relative priority of user and author style sheets. While author style sheets take precedence over user ones, if a user rule has !important applied to it, it will override even an author rule that also has !important applied to it.

Knowing this, let’s look at the final order, in ascending order of importance:

  1. User agent declarations,
  2. User declarations,
  3. Author declarations,
  4. Author !important declarations,
  5. User !important declarations.

This flexibility in priority is key because it allows users to override styles that could hamper the accessibility of a website. (A user might want a larger font or a different color, for example.)

2. Specificity Link

Every CSS rule has a particular weight (as mentioned in the introduction), meaning it could be more or less important than the others or equally important. This weight defines which properties will be applied to an element when there are conflicting rules.

Upon assessing a rule’s importance, the cascade attributes a specificity to it; if one rule is more specific than another, it overrides it.

If two rules share the same weight, source and specificity, the later one is applied.

2.1 How to Calculate Specificity? Link

There are several ways to calculate a selector’s specificity.

The quickest way is to do the following. Add 1 for each element and pseudo-element (for example, :before and :after); add 10 for each attribute (for example, [type=”text”]), class and pseudo-class (for example, :link or :hover); add 100 for each ID; and add 1000 for an inline style.

Let’s calculate the specificity of the following selectors using this method:

  • p.note
    1 class + 1 element = 11
  • #sidebar p[lang="en"]
    1 ID + 1 attribute + 1 element = 111
  • body #main .post ul li:last-child
    1 ID + 1 class + 1 pseudo-class + 3 elements = 123

A similar method, described in the W3C’s specifications, is to start with a=0, b=0, c=0 and d=0 and replace the numbers accordingly:

  • a = 1 if the style is inline,
  • b = the number of IDs,
  • c = the number of attribute selectors, classes and pseudo-classes,
  • d = the number of element names and pseudo-elements.

Let’s calculate the specificity of another set of selectors:

  • <p style="color:#000000;">
    a=1, b=0, c=0, d=0 → 1000
  • footer nav li:last-child
    a=0, b=0, c=1, d=3 → 0013
  • #sidebar input:not([type="submit"])
    a=0, b=1, c=1, d=1 → 0111
    (Note that the negation pseudo-class doesn’t count, but the selector inside it does.)

If you’d rather learn this in a more fun way, Andy Clarke drew a clever analogy between specificity and Star Wars5 back in 2005, which certainly made it easier for Star Wars fans to understand specificity. Another good explanation is “CSS Specificity for Poker Players,” though slightly more complicated.

CSS: Specificity Wars
Andy Clarke’s CSS Specificity Wars chart.

Remember that non-CSS presentational markup is attributed with a specificity of 0, which would apply, for example, to the font tag.

Getting back to the !important declaration, keep in mind that using it on a shorthand property is the same as declaring all of its sub-properties as !important (even if that would revert them to the default values).

If you are using imported style sheets (@import) in your CSS, you have to declare them before all other rules. Thus, they would be considered as coming before all the other rules in the CSS file.

Finally, if two selectors turn out to have the same specificity, the last one will override the previous one(s).

2.2 Making Specificity Work For You Link

If not carefully considered, specificity can come back to haunt you and lead you to unwittingly transform your style sheets into a complex hierarchy of unnecessarily complicated rules.

You can follow a few guidelines to avoid major issues:

  • When starting work on the CSS, use generic selectors, and add specificity as you go along;
  • Using advanced selectors doesn’t mean using unnecessarily complicated ones;
  • Rely more on specificity than on the order of selectors, so that your style sheets are easier to edit and maintain (especially by others).

A good rule of thumb can be found in Jim Jeffers’ article, “The Art and Zen of Writing CSS6”:

Refactoring CSS selectors to be less specific is exponentially more difficult than simply adding specific rules as situations arise.

3. Inheritance Link

A succinct and clear explanation of inheritance is in the CSS3 Cascading and Inheritance module7 specifications (still in “Working draft” mode):

Inheritance is a way of propagating property values from parent elements to their children.

Some CSS properties are inherited by the children of elements by default. For example, if you set the body tag of a page to a specific font, that font will be inherited by other elements, such as headings and paragraphs, without you having to specifically write as much. This is the magic of inheritance at work.

The CSS specification determines whether each property is inherited by default or not. Not all properties are inherited, but you can force ones to be by using the inherit value.

3.1 Object-Oriented Programming Inheritance Link

Though beyond the scope of this article, CSS inheritance shouldn’t be confused with object-oriented programming (OOP) inheritance. Here is the definition of OOP inheritance from Wikipedia8, and it makes clear that we are not talking about the same thing:

In object-oriented programming (OOP), inheritance is a way to form new classes […] using classes that have already been defined. Inheritance is employed to help reuse existing code with little or no modification. The new classes […] inherit attributes and behavior of the pre-existing classes. …

3.2 How Inheritance Works Link

When an element inherits a value from its parent, it is inheriting its computed value. What does this mean? Every CSS property goes through a four-step process when its value is being determined. Here’s an excerpt from the W3C specification9:

The final value of a property is the result of a four-step calculation: the value is determined through specification (the “specified value”), then resolved into a value that is used for inheritance (the “computed value”), then converted into an absolute value if necessary (the “used value”), and finally transformed according to the limitations of the local environment (the “actual value”).

In other words:

  1. Specified value
    The user agent determines whether the value of the property comes from a style sheet, is inherited or should take its initial value.
  2. Computed value
    The specified value is resolved to a computed value and exists even when a property doesn’t apply. The document doesn’t have to be laid out for the computed value to be determined.
  3. Used value
    The used value takes the computed value and resolves any dependencies that can only be calculated after the document has been laid out (like percentages).
  4. Actual value
    This is the value used for the final rendering, after any approximations have been applied (for example, converting a decimal to an integer).

If you look at any CSS property’s specification, you will see that it defines its initial (or default) value, the elements it applies to, its inheritance status and its computed value (among others). For example, the background-color specification states the following:

Name: background-color
Value: <color>
Initial: transparent
Applies to: all elements
Inherited: no
Percentages: N/A
Media: visual
Computed value: the computed color(s)

Confusing? It can be. So, what do we need to understand from all this? And why is it relevant to inheritance?

Let’s go back to the first sentence of this section, which should make more sense now. When an element inherits a value from its parent, it inherits its computed value. Because the computed value exists even if it isn’t specified in the style sheet, a property can be inherited even then: the initial value will be used. So, you can make use of inheritance even if the parent doesn’t have a specified property.

3.3 Using Inheritance Link

The most important thing to know about inheritance is that it’s there and how it works. If you ignore the jargon, inheritance is actually very straightforward.

Imagine you had to specify the font-size or font-family of every element, instead of simply adding it to the body element? That would cumbersome, which is why inheritance is so helpful.

Don’t break it by using the universal selector (*) with properties that inherit by default. Bobby Jack wrote an interesting post about this on his Five-Minute Argument blog. You don’t have to remember all of the properties that inherit, but you will in time.

Rarely does a CSS-related article not bring some kind of bad news about Internet Explorer. This article is no exception. IE supports the inherit value only from version 8, except for the direction and visibility properties. Great.

4. Using Your Tools Link

If you use tools like Firebug or Safari’s Web Inspector, you can see how a given cascade works, which selectors have higher specificity and how inheritance is working on a particular element.

For example, here below is Firebug in action, inspecting an element on the page. You can see that some properties are overridden (i.e. crossed out) by other more specific rules:

Firebug showing properties being overridden due to higher specificity
Firebug in action, informing you how specificity is working.

In the next shot, Safari’s Web Inspector shows the computed values of an element. This way, you can see the values even though they haven’t been explicitly added to the style sheet:

Safari Web Inspector showing computed values
With Safari’s Web Inspector (and Firebug), you can view the computed values of a particular element.

5. Conclusion Link

Hopefully this article has opened your eyes to (or has refreshed your knowledge of) CSS inheritance and specificity. We encourage you to read the articles cited below, as well as Smashing Magazine’s previous article on the topic10.

Even if you don’t think about them, these issues are present in your daily work as a CSS author. Especially in the case of specificity, it’s important to know how they affect your style sheets and how to plan for them so that they cause only minimal (or no) problems.

Resources And Further Reading Link


Footnotes Link

  1. 1
  2. 2
  3. 3
  4. 4
  5. 5
  6. 6
  7. 7
  8. 8
  9. 9
  10. 10
  11. 11
  12. 12
  13. 13
  14. 14
  15. 15
  16. 16
  17. 17
  18. 18
  19. 19
  20. 20
  21. 21

↑ Back to top Tweet itShare on Facebook

Inayaili de León is a London-based Portuguese web designer, specialist in cross-browser, semantic HTML and CSS, and clean, functional design. She writes frequently for well-known online and print publications and also on her own web design blog, Web Designer Notebook. In May 2011, she published a book, Pro CSS for High Traffic Websites, and she speaks frequently at local and international web conferences and meetups. She is currently working as a web designer on Canonical's Design team.

  1. 1

    very useful!!

  2. 2


    April 7, 2010 7:22 am

    Like Eric Meyer pointed out on Andy Clarke’s Star Wars specificity article, the use of addition is a bit misleading.

    For example, a selector with only 1 class would be seen as having a value of 10, (since 1 class equals 10), and a selector with 13 elements would be 13 (since each element has a value of 1). However, in this case, 13 is not greater than 10. 1 class still overrides 13 elements.

    It’s important to note that it’s more of 4 individual numerics with infinite base. So the example you used:

    1 class + 1 element = 11
    #sidebar p[lang=”en”]
    1 ID + 1 attribute + 1 element = 111
    body #main .post ul li:last-child
    1 ID + 1 class + 1 pseudo-class + 3 elements = 123

    Should be rewritten to be:

    1 class + 1 element = 0|0|1|1
    #sidebar p[lang=”en”]
    1 ID + 1 attribute + 1 element = 0|1|1|1
    body #main .post ul li:last-child
    1 ID + 1 class + 1 pseudo-class + 3 elements = 0|1|2|3

    Otherwise, people could become confused if you wrote a selector of…

    #sidebar li.first li li li li li li p span a

    Which, using your addition, would evaluate to:
    1 ID + 1 class + 10 attributes = 120, when it really equals 0|1|1|10 and has less specificity than “#sidebar .first .second”, which would also evaluate (using addition) to 120, but is actually 0|1|2|0.

    I know it’s confusing, and the likelihood of having 10 or more element selectors is extremely low, but I do feel it’s important to give an accurate representation of the values attached to selectors.

    Also, I like that you included mention of “!important”, but I think you missed an important part of the specificity mentioned.

    As stated, inline styles in your markup will override whatever is in your CSS, because it has a value of 1|0|0|0, and no matter how many ID’s you use in your selector, you can’t overpower it. However, using “!important” will allow you to override inline styles from your CSS.

    This is only sometimes useful, in case you’re overriding CSS added through a javascript api you don’t have any control over or something like that, but again, important to mention that it will work.

    Things like specificity and inheritance and how CSS cascades is really something that is often overlooked as far as front-end development goes, and I really think it should be included as part of the CSS 101 stuff, in that it should be taught when you’re initially learning CSS.

  3. 3

    Amber Weinberg

    April 7, 2010 7:54 am

    This is more pointed to something I read on another site, but seemed pretty relevant here. It gets pretty annoying when “experts” say that CSS is easy and anyone can do it. Yes, CSS basics are easy. But semantics, media stylesheets, browser compatibility, advanced selectors and complicated layouts aren’t. Anyone can change the color of the font, but CSS is more than basic styles, especially when it comes to large, complicated layouts, liquid sizes and handheld media devices. It’s something that takes years to really learn and anticipate just like anything else and it shouldn’t be devalued just because it’s easy to get your foot in the door.

  4. 4

    Jamal Nichols

    April 7, 2010 7:56 am

    Another CSS Article? Seriously? CSS Articles are such a dead horse. It’s a topic of very limited depth and everything that can be said about it has already been said. If someone hasn’t been developing sites for a while, pick up a decent book like “Bulletproof Web Design” (or any book by Cederholm), “CSS Mastery”, “Pro CSS & HTML Design Patterns”, and many more. Most of them are good.

  5. 5

    am only a beginner so idon’t know what are u guys talking about :)

  6. 6

    Lennard Schutter

    April 7, 2010 6:55 am

    Very good article! Thanks!

  7. 7

    Jay Dalisay

    April 7, 2010 7:00 am

    Useful indeed!

  8. 8

    Vladimir Carrer

    April 7, 2010 7:31 am

    Nice article Yaili, CSS Specificity is probably one of the most confusing concepts in CSS. Many people have difficulties understanding this principle.

    Maybe my CSS Specificity – Cheat Sheet can be also helpful to someone

  9. 9

    Irfan Suleman

    April 7, 2010 7:40 am

    worth reading, very good :)

  10. 10

    Ahh I’m not a pro web developer but just the other day I needed to find out why a button in a feedback form was not left aligned. I used the Firefox Web developer add-on and the tool you get in IE8 when you press F12. Exactly this cascading styles made it difficult for me to see what exactly “drives” the button position. I havn’t found it out yet (some hidden ajax loader stuff )but maybe this article will help me to get further.
    Thanks for the article!

    BTW: Inayaili de Léon, what a beautiful name!!

  11. 11

    Mark Stickley

    April 7, 2010 8:59 am

    Great article! There can never be enough articles like this because everyone needs to know what they talk about…

    I wrote an article for the BBC Web Developer Blog which touches on inheritance and specificity:

    One thing that I found when doing my research was that hardly any articles actually point out what Russell points out: that a single #id overrides as many .classes as you can throw at it, and so on with .classes vs elements etc. which is definitely worth noting.

    Very nice explanation and process detail. Keep up the good work :D

  12. 12

    Lucas Cepeda

    April 7, 2010 9:21 am

    From the text, the order importance was quite clear, but I think in the list the order is described wrong. Shouldn’t be “ascending” order of importance? 5 is more important than 1.

    Thanks for the nice article!

  13. 13

    A very worthy read, I enjoy these in-depth articles on web coding concepts. More diagrams/pictures to explain the concepts would have been nice, but maybe that’s just my learning style. Excellent work Inayaili!

  14. 14

    Beautifully explained… Thanks for making it very comprehensive with perfect examples…

  15. 15

    Inayaili de Leon

    April 7, 2010 12:40 pm

    Thank you, Lucas! Will you believe me if I say I only did that to see if you were paying attention? :P

    (Probably not…)

    I’ve just fixed the error.

  16. 16

    Inayaili de Leon

    April 7, 2010 12:45 pm

    You’re absolutely right. Although I would question the efficiency of a style sheet that has selectors with 13 classes! :)

    About the “!important” declaration, I could have probably been more clear in the article, even though I mention that it overrides anything — I have to confess it was rather hard to explain concepts that are already deeply ingrained in my mind in a way that made sense and not forget about relevant stuff.

    Thank you for taking the time to write up this comment, I really appreciate it.

  17. 17

    Inayaili de Leon

    April 7, 2010 12:49 pm

    Those are my feelings exactly. It takes many years to create complicated CSS layouts that you can be confident to be working cross-browser without even having to open IE and such. I can’t say I do that every single time, but I’m learning every day to get there.

    I’m a lot of times stunned with how horrible and fragile CSS can be created by developers of (very) complicated programming languages mainly due to the fact that they don’t face those issues every day.

    The simplicity is merely an illusion.

  18. 18

    Niels Matthijs

    April 7, 2010 1:26 pm

    CSS specificity is tricky, no matter how you look at it. It behaves differently from what a we normally expect when using the word “specificity”.

    The lacking key concept is “proximity”. The depth of elements within the DOM (or the distance between elements within the DOM) is never taken into account. That’s why “#idOnBody a” will have the same weight as “a#idThisLink”, something that is logical if you understand the CSS rules but still feels quite awkward.

    More details:

  19. 19

    All right, not CSS related, but I join @liebesiech on the fact that Inayaili de Léon is a very beautiful name! Very nice to pronounce :)

    Specificity and inheritance are so important when you want to write good CSS! Not always easy to grasp at first, but it comes with experience. Thanks for this helpful article!

  20. 20

    Jeremy Buff

    April 7, 2010 4:16 pm

    Really useful, but I could have sworn this was a repost? I thought I saw this before on here? In any event, thank you for taking the time to- not only write- but think about how to explain this best. :)

  21. 21


    April 7, 2010 4:45 pm

    Thank you Brukhar for sending me this very useful tutorial, “CSS Specificity and Inheritance – SmashingMagazine” link !! I am very grateful and committed to learning everything I can about creating a Class A Blog here on the web !! I have this website and many others bookmarked as great resources for me to learn from !! Everyone who shares dreams like mine should check this tutorial and website out for inspiration and techniques for creating an ultimate blog site, as well as many others too !! There are a number of other blogs such as Brukhar’s, Ayaz’s, Paul’s, Deepak’s and the list just keeps on going !! I offer my humble opinion to everyone…. learn everything you can about everything blog and website design related and study it well enough to where your confusion is limited to only “moments or hours”…. rather than getting “dazed and confused” for days or weeks !! :)

  22. 22

    John Faulds

    April 7, 2010 7:24 pm

    Use Firebug instead, that’ll give you a clearer idea of what styles are being applied.

  23. 23

    Very good article! Thanks!

  24. 24

    Hi John,
    Brilliant, thank you for the tip!

  25. 25

    Brilliant Article

    Also Web Designer Notebook is a very good resource :)

  26. 26

    Dan Sunderland

    April 8, 2010 3:41 am

    Excellent, cheers!

  27. 27

    Amos Vryhof

    April 8, 2010 5:48 pm

    I still hate the syntax of !important … coming from a programming background I see it as NOTimportant

  28. 28

    @Jamal …stop being a hater!
    @ Inayaili…great post, I love great articles on CSS.

  29. 29

    This is a great point, Amber. CSS is at least an order of magnitude more complicated than HTML, yet as soon as people learn HTML they want to be able to style things – understandably. I think there are definitely a lot of different levels of understanding – I was using CSS for several years before I really ‘got’ the positioning properties, for example. Specificity is one of those really complicated issues (especially combined with inheritance and the cascade) so it’s great to see an article such as this one covering the key points.

    And, yes, as with all CSS-related issues, Firebug makes things a LOT easier to understand :-)

  30. 30

    Douglas Gintz

    April 8, 2010 6:29 pm

    Good article. CSS is always a worthwhile topic. I build enterprise-level web apps for a living and CSS can often cause trouble in unexpected ways. I’m just waiting for the day when those responsible for browsers get on the same page. For as much control CSS gives you, it is way too convoluted as it stands. Fortunately, we have frameworks like jQuery and EXTJS that make cross-browser GUI development & DOM handling a little more bearable.

  31. 31

    You could save a lot of time if you just used TopStyle and it’s panel showing specificity

  32. 32

    Rasmus Fløe

    April 8, 2010 10:08 pm

    Great article – and comments!

    I haven’t been able to grok how to override useragent stylesheet declarations with !important in them (firefox input/button line-height I’m looking at you!). I’ve googled my fingers to bloody stubs trying to find anything regarding this with no luck.

    If anyone’s got a clue on this – please share!

  33. 33

    “Very limited depth” are you joking???? if you think you have mastered CSS you are seriously deluded. there are only a small handfull of people who are actually using css anywhere near its full potential.

  34. 34

    Arnoud ten Hoedt

    April 10, 2010 8:10 am

    Nice background article, but I am missing some hints to help me write more maintainable CSS, or actually prevent me from having to think about this kind of stuff, and be more productive.

    When websites get larger and complexer, there is a need to have a proper methodology to keep your CSS scale along, stay maintainable and high performing.

    From the Object Oriented CSS could be one of the methodologies.

  35. 35

    I agree DaveK. CSS is hell. It is a bunch of non-intuitive rules that contradict each other. You can tell this by the number of articles out there, the endless tips and tricks, and arguments among people who think they use CSS right.

    This is the best real programmers could come up with???

    Why not just call tables “grids” and be done with the semantic arguments? Make screen readers that don’t read the word “grid”. Is it that hard? I know CSS3 has some kind of new layout models. Have you read that? It looks like some kind of Atari 400 BASIC programming.

    God forbid you use a WYSIWG editor. You’ll be condemned to the lower depth of Hades. Can you imagine programming PostScript when Smashing Magazine produced it’s book (that still cracks me up)? Of course programmers would love that.

  36. 36

    I have to disagree about inheritance – it is pretty much exactly the same thing in JavaScript as it is in CSS. Both are a lot more complex than the pretty model that I was taught in college, but they are essentially the same thing.

  37. 37

    Great informative tutorials. Nice effort!!!

  38. 38

    You could save a lot of time if you just used TopStyle and it’s panel showing specificit

  39. 39

    Good article. CSS is always a worthwhile topic. I build enterprise-level web apps for a living and CSS can often cause trouble in unexpected ways. I’m just waiting for the day when those responsible for browsers get on the same page. For as much control CSS gives you, it is way too convoluted as it stands. Fortunately, we have frameworks like jQuery and EXTJS that make cross-browser GUI development & DOM handling a little more bearable.

  40. 40

    good one

  41. 41

    This is a greta article. There was a lot of helpful info in here. Thanks for sharing.

  42. 42

    There is for example a preprocessor that adds real oop inheritance to CSS

    it will add the extends keyword to your CSS syntax and makes it possible to inherit values from other classes or ids.

    .someClass {
    color: blue;
    width: 50%;
    .otherClass extends .someClass {
    width: 30%;
    otherClass will now have all properties of someClass. Additionally it locally overwrites the width to 30%.

    Multiple inheritance is also possible (seperated by colons).

    .foo extends #bar, #bar2, .class1 {

    Now foo will get all values of the two id’s plus the values of class1. For overwriting #bar will be weakest, as defined first and .class1 will be strongest, so it will override (if applicable) any values be earlier extended classes. If .foo has any local values, they will be strongest and override any extended values.

    See ECSS readme for further details about inheritance options and overriding rules:

  43. 43

    Ricardo Tabone

    April 2, 2013 5:50 am

    Very good article. In fact, you write many excellent articles and I must say “Parabéns!”

    I wonder why most of the literature on CSS dedicates little attention to inheritance and specificity.
    Being a an object oriented software designer, I always feel compelled to apply the same principles to everything I do and working with CSS is no differente.

    Obrigado pela sua dedicação!


↑ Back to top