Let me repeat again:
If a function doesn't have a HoldAll/HoldFirst/HoldRest/HoldAllComplete attribute, its argument(s) will always be evaluated before going into the function.
ReplaceAll (/.) doesn't have such attribute, so the whole {x, x^2, Length@x, Subsets[x]} evaluates before the replacement happens. (The order is from left to right, BTW. ) This can be checked with Trace:
Trace[{x, x^2, Length[x], Subsets[x]} /. x -> {1, 2, 3}]

If you want to check the evaluation of x and x^2, set TraceOriginal -> True, the output will be a bit more involved, though.
As we can see, Length@x evaluates to 0. This is expected. As mentioned in Details section of document of Length:
Length[expr] returns 0 whenever AtomQ[expr] is True.
Subsets[x] evaluates to itself with a warning Subsets::normal. Since the Subsets[x] is still there, once the replacement happens, it'll become Subsets[{1, 2, 3}] and further evaluates to the desired output.
Finally, in addition to the Hold & ReleaseHold technique shown in rhermans' answer, another (more advanced) way to adjust the evaluation order is to use Unevaluated:
Unevaluated@{x, x^2, Length[x], Subsets[x]} /. x -> {1, 2, 3}
(* {{1, 2, 3}, {1, 4, 9}, 3, {{}, {1}, {2}, {3}, {1, 2}, {1, 3}, {2, 3}, {1, 2, 3}}} *)
Lengthevaluates to be0; checkLength@x. Not sure what you mean when you say it does not evaluate. Also, the argument ofSubsethas to be a list, and currently it is not, hence the error. – bmf Feb 24 '23 at 10:09LengthandSubsetsevaluate after replacement? Then x will be List! And why we see right result ofSubsets? – lesobrod Feb 24 '23 at 10:11Length@xgives0. Is it possible that you want to writefoo[n_] := {x, x^2, Length@Range@n, Subsets[Range@n]} /. x -> Range@nand thenfoo[3]? – bmf Feb 24 '23 at 10:12