The composite type is clean design, but it does *not* help performance *at all*.

First of all, `float` translates to `float8` a.k.a. `double precision` in Postgres. You are building on a misunderstanding.  
The [`real`][1] data type occupies 4 byte (not 8). It has to be aligned at multiples of 4 bytes. 

Measure actual sizes with [`pg_column_size()`][2].

[**SQL Fiddle**][3] demonstrating actual sizes.

The composite type `real3d` occupies 36 bytes. That's:

    23 byte tuple header
    1 byte padding
    4 bytes real x
    4 bytes real y
    4 bytes real z
    ---
    36 bytes

If you embed that into a table, padding *may* have to be added. On the other hand the header of the type can be 3 byte smaller on disk. Representation on disk is typically a bit smaller than in RAM. Doesn't make a lot of difference.

More:

- https://dba.stackexchange.com/questions/42290/configuring-postgresql-for-read-performance/43142#43142
- [Calculating and saving space in PostgreSQL][4]

###Table layout

Use this equivalent design to reduce row size *substantially*:

        Column     |           Type           |                       Modifiers
    ---------------+--------------------------+---------------------------------
     id            | bigint                   | not null default nextval(...
     creation_time | timestamp with time zone | not null default now()
     edition_time  | timestamp with time zone | not null default now()
     user_id       | integer                  | not null
     project_id    | integer                  | not null
     location_x    | real                     | not null
     location_y    | real                     | not null
     location_z    | real                     | not null
     radius        | real                     | not null default 0
     skeleton_id   | integer                  | not null
     confidence    | smallint                 | not null default 5
     parent_id     | bigint                   |
     editor_id     | integer                  |

Test before and after to verify my claim:

    SELECT pg_relation_size('treenode') As table_size;
    
    SELECT avg(pg_column_size(t) AS avg_row_size
    FROM   treenode t;

More details:

- https://dba.stackexchange.com/questions/23879/measure-the-size-of-a-postgresql-table-row/23933#23933


  [1]: http://www.postgresql.org/docs/current/interactive/datatype-numeric.html
  [2]: http://www.postgresql.org/docs/current/interactive/functions-admin.html#FUNCTIONS-ADMIN-DBSIZE
  [3]: http://sqlfiddle.com/#!15/6dc9a/3
  [4]: http://stackoverflow.com/questions/2966524/calculating-and-saving-space-in-postgresql/7431468#7431468