diff --git a/examples/quickstart-tuto.py b/examples/quickstart-tuto.py
index 19f9b60cbbe558acb8691a386b194410fb53a0c4..810c2f2b5ea00f09c49c34147321dd3ed9382b8c 100644
--- a/examples/quickstart-tuto.py
+++ b/examples/quickstart-tuto.py
@@ -1,4 +1,4 @@
-from querybuilder.schemas import table, schema
+from querybuilder.schemas.helper import table, schema
 from querybuilder.queries.algebra.columns import (
     Value,
     Constant,
diff --git a/querybuilder/queries/algebra/columns.py b/querybuilder/queries/algebra/columns.py
index 04ce32cc6fc9ecde0fdd42fd0c82c245c9aadd09..1d1f959afd79613b18097fe25ee9158af0ebde29 100644
--- a/querybuilder/queries/algebra/columns.py
+++ b/querybuilder/queries/algebra/columns.py
@@ -109,14 +109,14 @@ def name_column(
     schema_name: Optional[str] = None,
     preserve_table_column: bool = False,
 ) -> Column:
+    if not name:
+        name = getattr(column, "name", None)
+
     if preserve_table_column and isinstance(column, TableColumn):
         return column.buildfrom(
-            column, relation_name=relation_name, schema_name=schema_name
+            column, name=name, relation_name=relation_name, schema_name=schema_name
         )
 
-    if not name:
-        name = getattr(column, "name", None)
-
     if name:
         return Named(
             sqltype=column.sqltype,
diff --git a/querybuilder/queries/algebra/relations.py b/querybuilder/queries/algebra/relations.py
index b64ba8afb5e1f49f01176debf748ac02d8133500..9813bc7d85fac3bdbf1bc7e0d6a41d3a51735f8d 100644
--- a/querybuilder/queries/algebra/relations.py
+++ b/querybuilder/queries/algebra/relations.py
@@ -126,7 +126,7 @@ class Fromable(Relation):
                     # assert isinstance(c, (int, str))
                     columns_to_select.append(self.columns.resolve(c))
         return querybuilder.queries.dql.Select(
-            from_=self, columns=columns_to_select, **kwargs
+            from_=self, selected_columns=columns_to_select, **kwargs
         )
 
     @method_accepting_lambdas
diff --git a/querybuilder/queries/dql.py b/querybuilder/queries/dql.py
index 0f055a6df7934fe388c4249e578c6984fa54e4ca..50b1050ece2f380be68f3f497c1188cab216479d 100644
--- a/querybuilder/queries/dql.py
+++ b/querybuilder/queries/dql.py
@@ -151,7 +151,7 @@ class Values(DQLQuery):
 
 class Select(DQLQuery):
     __slots__: tuple[str, ...] = (
-        "column_origins",
+        "selected_columns",
         "aliases",
         "from_",
         "where",
@@ -167,7 +167,7 @@ class Select(DQLQuery):
 
     def __init__(
         self,
-        columns: Sequence[qbcolumns.Column | qbcolumns.Star],
+        selected_columns: Sequence[qbcolumns.Column | qbcolumns.Star],
         aliases: Mapping[int, str] | Iterable[tuple[int, str]] = (),
         distinct: Optional[qbcolumns.Column | bool] = None,
         from_: Optional[qbrelations.Fromable] = None,
@@ -191,12 +191,12 @@ class Select(DQLQuery):
         self.offset = offset
         self.from_ = from_
 
-        super().__init__(columns=columns, **kwargs)
+        super().__init__(columns=selected_columns, **kwargs)
 
     @property
     def columns(self):
         columns = []
-        for i, c in enumerate(self.column_origins):
+        for i, c in enumerate(self.selected_columns):
             if isinstance(c, qbcolumns.Star):
                 columns.extend(self.from_.columns)
             else:
@@ -208,19 +208,21 @@ class Select(DQLQuery):
 
         return self._column_store_factory(columns)
 
-    def _init_columns(self, columns):
+    def _init_columns(self, selected_columns):
         for k in self.aliases.keys():
-            if 0 <= k < len(columns) and isinstance(columns[k], qbcolumns.Star):
+            if 0 <= k < len(selected_columns) and isinstance(
+                selected_columns[k], qbcolumns.Star
+            ):
                 raise KeyError("Cannot alias a * column")
-        for c in columns:
+        for c in selected_columns:
             if isinstance(c, qbcolumns.Star):
                 assert self.from_  # TODO: Maybe another exception would be better
                 break
 
-        self.column_origins = self._column_store_factory(columns)
+        self.selected_columns = self._column_store_factory(selected_columns)
 
     def accept(self, visitor, /):
-        for col in self.column_origins:
+        for col in self.selected_columns:
             visitor = col.accept(visitor)
         for res in (self.from_, self.where, self.groupby, self.having, self.orderby):
             if res:
@@ -230,7 +232,7 @@ class Select(DQLQuery):
 
     def descend(self, accumulator):
         accumulator = super().descend(accumulator)
-        for ocol in self.column_origins:
+        for ocol in self.selected_columns:
             accumulator = ocol.descend(accumulator)
 
         for res in (self.from_, self.groupby, self.having, self.orderby, self.where):
@@ -240,16 +242,20 @@ class Select(DQLQuery):
         return accumulator
 
     def set_selected_columns(
-        self, columns: Iterable[str | int | qbcolumns.Column | qbcolumns.Star], /
+        self,
+        selected_columns: Iterable[str | int | qbcolumns.Column | qbcolumns.Star],
+        /,
     ) -> Select:
         """Method for resetting selected columns of the query
 
+        Aliases are not preserved and Star is allowed.
+
         Parameters
         ----------
-        columns: Iterable[str | int | qbcolumns.Column | qbcolumns.Star]
+        selected_columns: Iterable[str | int | qbcolumns.Column | qbcolumns.Star]
             the specifications of the columns to select.  Each specification might be an
             index (int), a name (str), an explicit column, or the special operator Star.
-            In the two first cases, it is resolved within the `column_origins` store,
+            In the two first cases, it is resolved within the `selected_columns` store,
             using the `resolve` method.  You may want to consider using `set_columns` for
             setting columns using similar specifications that are resolved within the
             `columns` store context instead.  A side effect of the method is that all
@@ -276,22 +282,35 @@ class Select(DQLQuery):
         'SELECT t.y, 2, t.x FROM t'
 
         Indeed, in the list parameter `[2, Constant(int, 2), "x"]`, `2` stands for the
-        origin column of index 2 (ie, `sq.column_origins[2]`), and `"x"` stands for the
-        origin column that is unambiguously named "x" (ie, `sq.column_origins._["x"]`).
+        selected column of index 2 (ie, `sq.selected_columns[2]`), and `"x"` stands for the
+        selected column that is unambiguously named "x" (ie, `sq.selected_columns._["x"]`).
+
+        It is also possible to use `querybuilder.queries.algebra.columns.Star()`, or the
+        `"*"` shorthand, in the sequence of selected columns.
+        >>> from querybuilder.queries.algebra.columns import Star
+        >>> str(sq.set_selected_columns(["*", 2, Star(), "x"]))
+        'SELECT *, t.y, *, t.x FROM t'
+
         """
         cols: list[qbcolumns.Column | qbcolumns.Star] = []
-        for c in columns:
+        for c in selected_columns:
             if c == "*":
+                assert self.from_
                 cols.append(qbcolumns.Star())
-            elif isinstance(c, (qbcolumns.Column, qbcolumns.Star)):
+            elif isinstance(c, qbcolumns.Star):
+                assert self.from_
+                cols.append(c)
+            elif isinstance(c, qbcolumns.Column):
                 cols.append(c)
             else:
                 # assert isinstance(c, (int, str))
-                cols.append(self.column_origins.resolve(c))
+                cols.append(self.selected_columns.resolve(c))
         return self.set_aliases(())._set_columns(cols)
 
     def set_columns(self, columns: Iterable[str | int | qbcolumns.Column], /) -> Select:
-        """Method for resetting exposed (thus selected) columns of the query
+        """Method for resetting exposed columns of the query
+
+        Aliases are kept; Star is forbidden.
 
         Parameters
         ----------
@@ -301,7 +320,7 @@ class Select(DQLQuery):
             is resolved within the `columns` store, using the `resolve` method.  If the
             corresponding column was aliased, then the alias is kept.  The special Star
             operator is not allowed here, since the specifications are resolved according
-            to the exposed columns, and not their origins.
+            to the exposed columns, and not their selected origins.
 
         Related methods
         ---------------
@@ -344,8 +363,9 @@ class Select(DQLQuery):
             else:
                 orig_c = c
                 index = None
+
             if index is not None:
-                orig_c = self.column_origins[index]
+                orig_c = self.selected_columns[index]
                 alias = self.aliases.get(index)
                 if alias:
                     aliases[i] = alias
@@ -426,7 +446,7 @@ class Select(DQLQuery):
             clauses.AliasedColumn(c, self.aliases.get(i, None)).subtokenize(tokenizer)
             if isinstance(c, qbcolumns.Column)
             else c.subtokenize(tokenizer)
-            for i, c in enumerate(self.column_origins)
+            for i, c in enumerate(self.selected_columns)
         )
         if self.distinct:
             add_kwargs["distinct"] = clauses.DistinctColumn(self.distinct).subtokenize(
@@ -469,16 +489,12 @@ class Select(DQLQuery):
         return self.buildfrom(self, columns=columns)
 
     def _post_getstate(self, state):
-        state["columns"] = state.pop("column_origins")
+        state["columns"] = state.pop("selected_columns")
         return state
 
     def _substitute(self, substitutions: Mapping):
-        columns = map(
-            operator.methodcaller("substitute", substitutions),
-            self.column_origins,
-        )
-
-        d = dict(columns=list(columns))
+        columns = [c.substitute(substitutions) for c in self.selected_columns]
+        d = dict(columns=columns)
 
         for k in ("where", "distinct", "groupby", "orderby", "having", "from_"):
             res = getattr(self, k)
diff --git a/querybuilder/tests/queries/test_dql.py b/querybuilder/tests/queries/test_dql.py
index d8296f2ab4a93fbf182e7a956df7b38e8a8a7180..7b4ed1999639f55db5457b230ffc8011dc920de0 100644
--- a/querybuilder/tests/queries/test_dql.py
+++ b/querybuilder/tests/queries/test_dql.py
@@ -42,7 +42,7 @@ class TestSelect(TestDQL):
 
         expected_columns = [qbcolumns.Named(int, f"c{i}") for i in proj_indices]
 
-        assert expected_columns == list(proj.column_origins)
+        assert expected_columns == list(proj.selected_columns)
         assert {} == proj.aliases
 
     def test_set_columns_unaliased_columns_with_list_of_strings(self):
@@ -55,7 +55,7 @@ class TestSelect(TestDQL):
 
         expected_columns = [qbcolumns.Named(int, f"c{i}") for i in proj_indices]
 
-        assert expected_columns == list(proj.column_origins)
+        assert expected_columns == list(proj.selected_columns)
         assert {} == proj.aliases
 
     def test_set_columns_unaliased_columns_with_list_of_columns(self):
@@ -68,7 +68,7 @@ class TestSelect(TestDQL):
 
         expected_columns = [qbcolumns.Named(int, f"c{i}") for i in proj_indices]
 
-        assert expected_columns == list(proj.column_origins)
+        assert expected_columns == list(proj.selected_columns)
         assert {} == proj.aliases
 
     def test_set_columns_unaliased_columns_with_list_of_mixed_specifications(self):
@@ -88,7 +88,7 @@ class TestSelect(TestDQL):
         expected_columns = [qbcolumns.Named(int, f"c{i}") for i in proj_indices]
         expected_columns.append(qbcolumns.Constant(int, 3))
 
-        assert expected_columns == list(proj.column_origins)
+        assert expected_columns == list(proj.selected_columns)
         assert {} == proj.aliases
 
     def test_set_columns_aliased_columns_with_list_of_integers(self):
@@ -103,7 +103,7 @@ class TestSelect(TestDQL):
         expected_columns = [qbcolumns.Named(int, f"c{i}") for i in proj_indices]
         expected_aliases = {0: "a0", 1: "a4", 3: "a0"}
 
-        assert expected_columns == list(proj.column_origins)
+        assert expected_columns == list(proj.selected_columns)
         assert expected_aliases == proj.aliases
 
     def test_set_columns_aliased_columns_with_list_of_strings(self):
@@ -118,7 +118,7 @@ class TestSelect(TestDQL):
         expected_columns = [qbcolumns.Named(int, f"c{i}") for i in proj_indices]
         expected_aliases = {0: "a0", 1: "a4", 3: "a0"}
 
-        assert expected_columns == list(proj.column_origins)
+        assert expected_columns == list(proj.selected_columns)
         assert expected_aliases == proj.aliases
 
     def test_set_columns_aliased_columns_with_list_of_columns(self):
@@ -134,7 +134,7 @@ class TestSelect(TestDQL):
         expected_columns = [qbcolumns.Named(int, f"c{i}") for i in proj_indices]
         expected_aliases = {0: "a0", 1: "a4", 3: "a0"}
 
-        assert expected_columns == list(proj.column_origins)
+        assert expected_columns == list(proj.selected_columns)
         assert expected_aliases == proj.aliases
 
     def test_set_columns_aliased_columns_with_list_of_mixed_specifications(self):
@@ -151,7 +151,7 @@ class TestSelect(TestDQL):
         expected_columns.append(qbcolumns.Constant(int, 3))
         expected_aliases = {0: "a0", 1: "a4", 3: "a0"}
 
-        assert expected_columns == list(proj.column_origins)
+        assert expected_columns == list(proj.selected_columns)
         assert expected_aliases == proj.aliases
 
     def test_set_selected_columns_unaliased_columns_with_list_of_integers(self):
@@ -164,7 +164,7 @@ class TestSelect(TestDQL):
 
         expected_columns = [qbcolumns.Named(int, f"c{i}") for i in proj_indices]
 
-        assert expected_columns == list(proj.column_origins)
+        assert expected_columns == list(proj.selected_columns)
         assert {} == proj.aliases
 
     def test_set_selected_columns_unaliased_columns_with_list_of_strings(self):
@@ -177,7 +177,7 @@ class TestSelect(TestDQL):
 
         expected_columns = [qbcolumns.Named(int, f"c{i}") for i in proj_indices]
 
-        assert expected_columns == list(proj.column_origins)
+        assert expected_columns == list(proj.selected_columns)
         assert {} == proj.aliases
 
     def test_set_selected_columns_unaliased_columns_with_list_of_columns(self):
@@ -190,7 +190,7 @@ class TestSelect(TestDQL):
 
         expected_columns = [qbcolumns.Named(int, f"c{i}") for i in proj_indices]
 
-        assert expected_columns == list(proj.column_origins)
+        assert expected_columns == list(proj.selected_columns)
         assert {} == proj.aliases
 
     def test_set_selected_columns_unaliased_columns_with_list_of_mixed_specifications(
@@ -212,7 +212,7 @@ class TestSelect(TestDQL):
         expected_columns = [qbcolumns.Named(int, f"c{i}") for i in proj_indices]
         expected_columns.append(qbcolumns.Constant(int, 3))
 
-        assert expected_columns == list(proj.column_origins)
+        assert expected_columns == list(proj.selected_columns)
         assert {} == proj.aliases
 
     def test_set_selected_columns_aliased_columns_with_list_of_integers(self):
@@ -226,7 +226,7 @@ class TestSelect(TestDQL):
 
         expected_columns = [qbcolumns.Named(int, f"c{i}") for i in proj_indices]
 
-        assert expected_columns == list(proj.column_origins)
+        assert expected_columns == list(proj.selected_columns)
         assert not proj.aliases
 
     def test_set_selected_columns_aliased_columns_with_list_of_strings(self):
@@ -240,7 +240,7 @@ class TestSelect(TestDQL):
 
         expected_columns = [qbcolumns.Named(int, f"c{i}") for i in proj_indices]
 
-        assert expected_columns == list(proj.column_origins)
+        assert expected_columns == list(proj.selected_columns)
         assert not proj.aliases
 
     def test_set_selected_columns_aliased_columns_with_list_of_columns(self):
@@ -255,7 +255,7 @@ class TestSelect(TestDQL):
 
         expected_columns = [qbcolumns.Named(int, f"c{i}") for i in proj_indices]
 
-        assert expected_columns == list(proj.column_origins)
+        assert expected_columns == list(proj.selected_columns)
         assert not proj.aliases
 
     def test_set_selected_columns_aliased_columns_with_list_of_mixed_specifications(
@@ -273,7 +273,7 @@ class TestSelect(TestDQL):
         expected_columns = [qbcolumns.Named(int, f"c{i}") for i in proj_indices]
         expected_columns.append(qbcolumns.Constant(int, 3))
 
-        assert expected_columns == list(proj.column_origins)
+        assert expected_columns == list(proj.selected_columns)
         assert not proj.aliases
 
     def test_column_property(self):