FSM Full Stack Masterclass
Platform under construction
HTML course badge

HTML Data

Intermediate

HTML Tables

Learn HTML Tables with practical examples for tables, lists, structured data relationships, accessibility, SEO and live practice.

HTML data structures

Tables are for relationships between data, not for page layout.

A table is useful when information belongs in rows and columns. Prices, schedules, comparison data, analytics, invoices and technical specifications are normal table use cases.

Good table markup is not only about making boxes on screen. The browser, screen readers and search engines need to understand which cells are labels, which cells are values and what the table is about.

The most important mindset is this: if the data still makes sense as a spreadsheet, a table is probably a good choice. If you only want columns for design, use CSS layout instead.

table

The wrapper for tabular data.

caption

A clear title or short explanation for the table.

thead, tbody, tfoot

Optional groups that make larger tables easier to understand.

tr, th, td

Rows, header cells and normal data cells.

Table anatomy

A table should explain relationships between data cells.

A table is useful when the reader needs to compare values across rows and columns. The HTML should preserve those relationships so visual users, keyboard users and screen reader users can all understand the same data.

<th scope="col">Price</th>
Table <table>

The container for data that belongs in rows and columns.

Caption <caption>

A short title that explains what the table compares.

Header cell <th scope="col">

A header cell names a row or column so the data has context.

Data cell <td>

A data cell contains the actual value connected to headers.

Use a table

When users compare structured data across rows and columns.

Use a list

When items belong together but do not need row-and-column comparison.

Use cards

When each item is a standalone object and comparison is not the main task.

Syntax and structure

A useful table needs a caption, rows and real header cells.

Use th for labels and td for values. Use scope when a header clearly labels a row or column.

Accessible pricing table

<table>
  <caption>Driving lesson prices</caption>
  <thead>
    <tr>
      <th scope="col">Item</th>
      <th scope="col">Duration</th>
      <th scope="col">Price</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <th scope="row">Single lesson</th>
      <td>60 minutes</td>
      <td>EUR 75</td>
    </tr>
  </tbody>
</table>

Table used as layout

<table>
  <tr>
    <td><h1>Hero title</h1></td>
    <td><img src="car.jpg" alt=""></td>
  </tr>
</table>

HTML quick reference

Reusable examples for quick reference.

Use these patterns when you need the syntax quickly. Each example has its own anchor, so search engines and readers can land directly on the exact pattern instead of only at the top of the lesson.

Semantic pattern

HTML pattern 1

A clean version of the markup from this lesson. Use it when you need the correct HTML shape quickly.

<table>
  <caption>Driving lesson prices</caption>
  <thead>
    <tr>
      <th scope="col">Item</th>
      <th scope="col">Duration</th>
      <th scope="col">Price</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <th scope="row">Single lesson</th>
      <td>60 minutes</td>
      <td>EUR 75</td>
    </tr>
  </tbody>
</table>
What this gives you

Meaningful markup that stays understandable before CSS and JavaScript are added.

Editable lab starter

HTML pattern 2

The starting point from the practice lab. Change the HTML first, then use CSS only for presentation.

<main class="demo-card">
  <h1>Lesson prices</h1>
  <table>
    <caption>Example lesson price list</caption>
    <thead>
      <tr><th scope="col">Item</th><th scope="col">Includes</th><th scope="col">Price</th></tr>
    </thead>
    <tbody>
      <tr><th scope="row">Start package</th><td>15 lessons and exam</td><td>EUR 1425</td></tr>
      <tr><th scope="row">Single lesson</th><td>60 minutes</td><td>EUR 75</td></tr>
    </tbody>
  </table>
</main>

<style>
body {
  margin: 0;
  min-height: 100vh;
  display: grid;
  place-items: center;
  font-family: Inter, system-ui, sans-serif;
  background: #07111f;
  color: white;
}

.demo-card {
  width: min(820px, calc(100% - 32px));
  padding: 34px;
  border-radius: 24px;
  background: #101a2d;
  box-shadow: 0 30px 80px rgba(0, 0, 0, 0.3);
}

h1 {
  margin: 0 0 18px;
  font-size: clamp(32px, 6vw, 54px);
  line-height: 1;
}

table {
  width: 100%;
  border-collapse: collapse;
  color: #f7f7f4;
}

caption {
  caption-side: top;
  margin-bottom: 12px;
  color: #8cffc1;
  font-weight: 900;
  text-align: left;
}

th, td {
  border-bottom: 1px solid rgba(255, 255, 255, 0.14);
  padding: 13px 14px;
  text-align: left;
  vertical-align: top;
}

th {
  color: #8cffc1;
  font-weight: 900;
}

ul, ol {
  display: grid;
  gap: 10px;
  margin: 0;
  padding-left: 24px;
  color: #cfd8e6;
}

li::marker {
  color: #8cffc1;
  font-weight: 900;
}

dl {
  margin: 0;
}
</style>
What this gives you

A complete practice snippet that shows how the HTML behaves in context.

Pattern to avoid

HTML pattern 3

A weak pattern from the lesson. Use it as a warning sign when reviewing real pages.

<table>
  <tr>
    <td><h1>Hero title</h1></td>
    <td><img src="car.jpg" alt=""></td>
  </tr>
</table>
What this gives you

A recognizable mistake you can search for and refactor.

Rules that matter

Data HTML should preserve relationships, not only appearance.

Tables and lists are small elements with big structural value. They help users scan, compare, follow steps and understand how pieces of information belong together.

Use tables for data

If the content is layout, use CSS grid or flexbox instead.

Add a caption

A caption gives the table a readable subject and helps assistive technology.

Use th for labels

Bold td text is not the same as a real header cell.

Group larger tables

thead, tbody and tfoot make repeated data easier to scan and maintain.

Keep cell content clear

A table should not become a dumping ground for full page sections.

Test narrow screens

Tables often need scrolling, simplified columns or responsive treatment.

Production thinking

Structured data markup affects accessibility, SEO and maintainability.

Why does this matter?

Tables matter because data loses value when the relationship between values is unclear. Strong table markup keeps that relationship visible to users and machines.

Accessibility

Screen reader users rely on header relationships. Correct th, scope and caption markup turns a visual grid into understandable data.

Production note

For large tables, plan sorting, filtering, sticky headers, horizontal scroll and export behavior early. The HTML structure is the foundation.

SEO note

Search engines can understand structured information better when table content is real text with clear headers and a relevant caption.

Live code lab

Change the code and run the example.

Edit the HTML or CSS, then use Run to refresh the preview. The preview is isolated, so links and forms stay inside this practice area.

Mini assignment

Try this now.

  • Add a third row for an exam fee.
  • Change one td that acts as a label into a real th with scope="row".
  • Add a short caption that explains the table in one sentence.

Practice assignment

Do this before moving to the next lesson.

  1. Create a table for a course schedule or price list.
  2. Use caption, thead, tbody, th and td correctly.
  3. Explain why this content is table data and not layout.

Try it yourself

Build a clean pricing table

Live preview

Self-check

Before you continue, prove that you own this lesson.

Intermediate

Do not only read this page. Answer these questions out loud or write the answers in your own notes. If one answer feels vague, revisit the examples before moving on.

  1. Can you explain why tables are for data and not layout?
  2. Can you connect th cells to data cells with scope?
  3. Can you decide when a caption helps the reader understand the table?
  4. Can you avoid colspan or rowspan when it makes the data harder to read?
  5. Can you make a wide table usable on a small screen?