Short answer

An EPSG code is a short integer that points to a specific coordinate reference system (CRS) in the EPSG Geodetic Parameter Dataset, a public registry maintained by the IOGP. Instead of describing a datum, ellipsoid, units, and projection by hand, you cite a number, EPSG:4326 for WGS84 lon/lat, EPSG:3857 for Web Mercator, EPSG:32631 for UTM zone 31N, and any compliant software resolves the full definition. The code is the unambiguous shorthand that lets two systems agree on exactly what a coordinate pair means.

What the registry actually contains

"EPSG" stands for the European Petroleum Survey Group, which created the dataset; it is now stewarded by the International Association of Oil & Gas Producers (IOGP). The registry is broader than just coordinate reference systems. It assigns codes to several kinds of object:

  • Coordinate reference systems (e.g. 4326, 32631), the entries most people mean by "EPSG code."
  • Datums (e.g. 6326 for WGS84), which fix the model and orientation of the Earth.
  • Ellipsoids (e.g. 7030 for the WGS84 ellipsoid GRS80-derived spheroid), the mathematical shape.
  • Coordinate operations / transformations (e.g. datum shifts between NAD27 and NAD83), the recipes for moving between systems.

So when software resolves EPSG:32631 it is not just reading "UTM 31N"; it pulls a chain: a projected CRS, built on the WGS84 geographic CRS, on the WGS84 datum, on a defined ellipsoid, with a Transverse Mercator projection parameterized to a central meridian of 3°E, false easting 500,000 m, and meter units. The code compresses all of that into five digits.

Geographic vs projected codes

The single most important property of a CRS, and the one that trips people up, is whether it is geographic or projected.

A geographic CRS like EPSG:4326 (WGS84) expresses position as longitude and latitude in degrees on an ellipsoid. Degrees are angular, not metric, and their ground size varies: one degree of latitude is roughly 111 km everywhere, but one degree of longitude shrinks from about 111 km at the equator to 0 at the poles. You cannot reliably measure distance or area directly in a geographic CRS.

A projected CRS like EPSG:32631 (UTM 31N) flattens the ellipsoid onto a plane and expresses position in meters (easting, northing). Now distance and area are straightforward Euclidean calculations, accurate within the projection's zone of validity. UTM keeps distortion under roughly 0.1% near a zone's central meridian, which is why it is the workhorse for regional measurement.

The rule that follows: store and exchange in a geographic CRS if you like, but transform into an appropriate projected CRS before you measure anything.

The UTM numbering trick

UTM codes follow a pattern worth memorizing because it saves constant lookups. The world is divided into 60 UTM zones, each 6 degrees of longitude wide. For WGS84:

  • Northern hemisphere: EPSG = 32600 + zone, so zone 31N is 32631.
  • Southern hemisphere: EPSG = 32700 + zone, so zone 56S is 32756.

To find the zone from a longitude: zone = floor((lon + 180) / 6) + 1. London at about 0°W is zone 30 → EPSG:32630. Singapore near 104°E is zone 48N → EPSG:32648. Sydney near 151°E, southern hemisphere, is zone 56S → EPSG:32756. (Note these all assume the WGS84 datum; national grids on other datums have entirely separate codes, e.g. EPSG:27700 for British National Grid on OSGB36.)

Worked example: assign vs reproject

You receive survey.shp. It opens but plots in the wrong place. Two very different fixes exist, and choosing the wrong one corrupts the data.

First, diagnose by looking at the coordinate values, not the filename. Open the attribute table or ogrinfo -al -so survey.shp. If eastings are around 450,000 and northings around 5,400,000, those are meters: this is UTM-like data. If values are like 2.35 and 48.85, those are degrees: lon/lat.

Case A: metadata is missing, coordinates are correct. The numbers are genuine UTM 31N meters but the .prj is absent so software defaults to nothing. You assign (define) the CRS, this changes no coordinates:

# GDAL: define the CRS without moving any coordinate
ogr2ogr -a_srs EPSG:32631 survey_defined.shp survey.shp
-- PostGIS equivalent: stamp the correct SRID on unstamped geometry
UPDATE survey SET geom = ST_SetSRID(geom, 32631);

Case B: coordinates are in one CRS, you need another. The data is correctly defined as UTM 31N but your project is in WGS84. You reproject (transform), this recomputes every coordinate:

# GDAL: transform from source CRS to target CRS
ogr2ogr -t_srs EPSG:4326 survey_wgs84.shp survey.shp
-- PostGIS equivalent
SELECT id, ST_Transform(geom, 4326) AS geom FROM survey;

The deadly mistake is using Case A's assign operation to "fix" a Case B problem: stamping EPSG:4326 onto data that is actually in UTM meters leaves 450,000 sitting where a longitude should be, sending every feature off the coast of West Africa.

Codes worth memorizing

A handful of codes cover most day-to-day work, and recognizing them on sight prevents a lot of confusion:

  • EPSG:4326 — WGS84 geographic (lon/lat degrees). The lingua franca for data exchange, GPS, and GeoJSON. Not for measurement.
  • EPSG:3857 — Web Mercator (meters). The projection of nearly every web basemap (Google, OSM, Esri tiles). Great for display, badly distorted for area, so avoid for analysis.
  • EPSG:4979 / EPSG:4978 — WGS84 3D geographic and geocentric (ECEF) variants, encountered in GNSS and geodesy.
  • EPSG:326## / 327## — WGS84 UTM north / south zones, the standard for regional metric work.
  • National grids — EPSG:27700 (British National Grid), EPSG:2154 (RGF93 Lambert-93, France), EPSG:25832 (ETRS89 / UTM 32N, much of Europe), EPSG:5070 (NAD83 Conus Albers, US national-scale equal area). These sit on regional datums, not WGS84, so transforming to or from them may involve a datum shift.

The datum point is easy to miss and expensive to get wrong: two CRSs can both be "UTM 32N" but on different datums (WGS84 vs ETRS89 vs NAD83), and the offset between them can be a meter or more, which matters for survey-grade work. The EPSG code disambiguates exactly which one you mean, and the registry also holds the transformation between them.

Common pitfalls and why they happen

  • Measuring in EPSG:4326. Distances and areas come out in degree-based nonsense because the units are angular. Transform to UTM first.
  • Using EPSG:3857 (Web Mercator) for analysis. It looks familiar from basemaps, but its area distortion grows enormously with latitude (Greenland looks larger than Africa). Fine for display, wrong for measurement.
  • Assigning when you should transform. Changes the label, not the numbers, and silently relocates data. See Case A vs B above.
  • Ignoring the area of use. Every projected CRS has a valid extent; UTM 31N is meaningless for data in Japan. Check the bounding box, e.g. on epsg.io.
  • Assuming all "WGS84" is one thing. EPSG:4326 has realizations and datum ensembles; for sub-meter work the specific realization and any datum transformation matter.
  • Forgetting vertical CRS. Elevation has its own datum and units (e.g. EGM2008, NAVD88); a horizontal EPSG code says nothing about height.

QA and validation

  • After defining or transforming, overlay the layer on a trusted reference (a national basemap, a known control point) and confirm it lands where it should.
  • Measure a known distance or area in the working CRS and compare to a published value; large error means the CRS is wrong, not the geometry.
  • Inspect coordinate ranges against the CRS's expected units before trusting the metadata.
  • Record source CRS, processing CRS, and output CRS, plus any datum transformation used, in the project notes; epsg.io and projinfo EPSG:32631 (from PROJ) give the authoritative definition.

Bathyl perspective

We treat the EPSG code as a contract, not a label: every layer that enters a project carries a verified code, and we distinguish "define the CRS" from "transform the CRS" on every import, because conflating them is the quiet source of most misplaced data. A documented CRS chain from source to output is what lets a second analyst reproduce a measurement without guessing.

Related reading

Sources