By Docify

Named vs Numeric HTML Entities: Ampersand First

• 6 min read

A named character reference is a mnemonic (<). A numeric one is the Unicode code point: decimal < or hex <. Encode writes & first so later passes cannot double-escape an entity. Apostrophe is ' because HTML 4.01 never defined '. Decode expands those five names plus numeric refs — not   and not the full HTML5 table. Nothing is uploaded.

Markup needs a way to write the characters that would otherwise start a tag or an entity. The live HTML encoder escapes five of them and decodes a small, named subset plus numeric references. This page names the three reference forms, the HTML 4.01 ' gap, and what a browser innerHTML parser would do that this tool does not.

Three ways to write the same character

Named: mnemonic, case-sensitive

HTML calls these named character references (HTML 4.01 said “character entity references”). The form is &name;. The five markup-significant names the live decoder accepts are amp (U+0026), lt (U+003C), gt (U+003E), quot (U+0022), and apos (U+0027). Names are case-sensitive. HTML5 also defines < for the same less-than; Docify does not expand that uppercase form.

< → U+003C

Decimal: &#D;

HTML 4.01 §5.3.1: “&#D;” is the ISO 10646 (Unicode) decimal code point. Less-than is 60, ampersand is 38, apostrophe is 39. The live decoder parses the digits with Number.parseInt(..., 10) and then String.fromCodePoint. Zero, negative values, and anything above U+10FFFF stay as written.

< → U+003C

Hex: &#xH; (XML wants lowercase x)

The same code point in hex: less-than is 3C. HTML 4.01 allows &#xH; or &#XH;. XML 1.0 requires a lowercase x. Hex digits themselves are case-insensitive (3C and 3c). Encode never writes numeric refs for &, <, >, or " — only the apostrophe is numeric.

&#x3C; → U+003C

Ampersand first, apostrophe numeric

Why & is replaced first

Every character reference begins with &. If you first turn < into &lt; and then escape every remaining ampersand, that entity becomes &amp;lt;. Decoding once yields the six characters &lt;, not a less-than. Encode therefore replaces & with &amp; before <, >, ", and the apostrophe. Non-ASCII letters stay as themselves — this is not UTF-8 percent-encoding.

5 < 10 & 10 > 5 → 5 &lt; 10 &amp; 10 &gt; 5

HTML 4.01 has no &apos;

W3C HTML 4.01 §24 ships three entity sets: Latin-1 (including &nbsp; U+00A0 and &copy; U+00A9), symbols and Greek, and markup-significant names. Those markup names include &amp;, &lt;, &gt;, and &quot;. There is no &apos;. XML 1.0 predefined five entities and added it. WHATWG HTML’s named-character table later maps apos; to U+0027. A document served as HTML 4.01 may show the six characters &apos; literally. Decimal &#39; and hex &#x27; are the same apostrophe in HTML 4.01, XML, and HTML5, so Encode always writes &#39;. Decode still accepts &apos;.

What Decode does not parse

Not the HTML 4.01 or WHATWG named tables

HTML 4.01’s Latin-1 list includes &nbsp;. WHATWG HTML lists more than two thousand named references (including many without a trailing semicolon, for legacy pages). Docify decode is a regex on those five names plus &# decimal or &#x hex, then String.fromCodePoint for scalars 1–0x10FFFF. Surrogates U+D800–U+DFFF stay written. So &nbsp; and &copy; remain those strings unless you wrote the numeric form &#160; or &#xA0;.

&nbsp; stays &nbsp; · &#160; → U+00A0

Not innerHTML, not a sanitizer

Assigning a string to innerHTML parses markup: tags run, the full HTML named-entity table applies, and a <script> or event-handler attribute is a different job. This page does not do that. It is also not encodeURI or encodeURIComponent (spaces stay spaces; they do not become %20). Escaping five characters is not XSS protection and not a HTML sanitizer. Encode and Decode are buttons, not as-you-type.

Escape or decode the five markup characters

Ampersand first. Apostrophe is &#39;. Nothing is uploaded.

Use HTML Encoder →

FAQ

What is the difference between named and numeric character references?
A named reference uses a mnemonic between & and ; — &lt; is U+003C. A numeric reference uses the Unicode code point: decimal &#60; or hexadecimal &#x3C; (HTML also allows &#X3C;). XML 1.0 requires a lowercase x. All three decode to the same less-than sign. Names are case-sensitive: &LT; is a different HTML5 name; Docify decode only accepts the five lowercase names amp, lt, gt, quot, and apos.
Why must Encode replace & first?
If you escape < to &lt; and then replace every &, the already-written &lt; becomes &amp;lt;. A later decode of that string yields the characters & l t ;, not <. Encoding & first (&amp;) means later < > " replacements cannot rewrite an existing entity. The live encoder does that five-step replace in that order.
Why is the apostrophe &#39; instead of &apos;?
HTML 4.01 section 24 lists Latin-1, symbol, and markup-significant names including &amp;, &lt;, &gt;, and &quot; — not &apos;. XML 1.0 predefined five entities and included &apos;. WHATWG HTML later added apos as U+0027. &#39; and &#x27; are the same code point and work in HTML 4.01, XML, and HTML5. Encode always writes &#39;. Decode still accepts &apos;, &#39;, and &#x27;.
Does Decode expand &nbsp; or the rest of the HTML named-entity table?
No. Decode expands only amp, lt, gt, quot, and apos, plus well-formed decimal or hex numeric references via String.fromCodePoint for Unicode scalars 1–0x10FFFF. Surrogate code points U+D800–U+DFFF and out-of-range values stay written. &nbsp; (U+00A0, HTML 4.01 Latin-1) and &copy; stay as those strings. This is not innerHTML, not a DOM parser, and not XSS protection.

Related