Forum > Suggestions

Custom type for Nil

<< < (2/10) > >>

MarkMLl:

--- Quote from: Warfley on March 11, 2022, 06:45:11 pm ---Ah sorry, sl is of type TStringList:

--- Code: Pascal  [+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i < x.length; i++) { x[i].style.maxHeight='none'; x[i].style.height = Math.min(x[i].clientHeight+15,306)+'px'; x[i].style.resize = "vertical";}};} ---var  sl: TStringList;begin  sl := nil;  sl := Pointer(0);end;
--- End quote ---

But you also get an error there if you try to assign an object to it, specifically:


--- Code: Text  [+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i < x.length; i++) { x[i].style.maxHeight='none'; x[i].style.height = Math.min(x[i].clientHeight+15,306)+'px'; x[i].style.resize = "vertical";}};} ---signalstore.pas(151,22) Error: Incompatible types: got "TObject" expected "TStringList" 
You can, OTOH, do this:


--- Code: Pascal  [+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i < x.length; i++) { x[i].style.maxHeight='none'; x[i].style.height = Math.min(x[i].clientHeight+15,306)+'px'; x[i].style.resize = "vertical";}};} ---sl := TStringList(Pointer(0)); 
Or this:


--- Code: Pascal  [+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i < x.length; i++) { x[i].style.maxHeight='none'; x[i].style.height = Math.min(x[i].clientHeight+15,306)+'px'; x[i].style.resize = "vertical";}};} ---sl := TStringList(TObject(Pointer(0))); 
So your example is far more about overlaying assignment to a class instance than it is about nil, and might even be entangled with the special behaviour of instances in that they're implicitly dereferenced (which is, obviously, compiler magic of the sort you're uneasy about).

MarkMLl

PascalDragon:

--- Quote from: Warfley on March 11, 2022, 02:09:07 pm ---So I was thinking, why could that not be opend to the programmers to also use, by making nil it's own type, e.g. TNil. This type would than through compilermagic, be implicetly convertable to all the use-cases of nil (which already is using compiler magic to be compatible in these cases),  but would allow to use nil for custom types through strong typechecking:
--- End quote ---

This was already rejected four weeks ago.

Warfley:
But the reasoning in this issue does only consider nil as function return type, with the last comment being:

--- Quote ---Adding a special kind of type that can only be used for function result variables
--- End quote ---
And yes, if this type would only be usable for return values, I would completely agree. But I argue that there are loads of valid use-cases, when you can use this as a parameter type for overloaded functions and operators

Not only with the example of nullable from my original post. Take dynamic arrays. You cann assign nil to a dynamic array because of compiler magic, but if you want to create your own dynamic array type, e.g. using managed records, you can't make them nil assignable. This brings this weird disconnect where you the compiler provides features that you could closely emulate, but not fully, because the compiler maigc won't let you. Like if you wanted to extend the dynamic types, string and array, with a dynamic dictionairy or set type, you simply can't because the compiler won't let you create the same features, it allows in other places.
Other use-cases would be smart pointers, any other datastructures that have an "empty" state. The concept of signalizing emptyness at compiletime can be really usefull, not just for assignments, but also for function calls (e.g. for optimisation, where when you cann a function with nil as parameter, the compiler will chose a different function such that you do not have to dispatch at runtime)

MarkMLl:

--- Quote from: Warfley on March 12, 2022, 07:46:36 pm ---But I argue that there are loads of valid use-cases, when you can use this as a parameter type for overloaded functions and operators

--- End quote ---

Untested code for illustration purposes:


--- Code: Pascal  [+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i < x.length; i++) { x[i].style.maxHeight='none'; x[i].style.height = Math.min(x[i].clientHeight+15,306)+'px'; x[i].style.resize = "vertical";}};} ---type  TNonTrivialRecord= ... function something(var ntr1: TNonTrivialRecord; var ntr2: TNonTrivialRecord): boolean; function something(nntr: TNil; var ntr2: TNonTrivialRecord): boolean; 
Assuming that something() corresponds to a C function being translated that expects two pointers to TNonTrivialRecord as parameters, this allows the Pascal compiler to apply full type checking etc. when it's called. In C, a null pointer could be passed if one of the parameters was to be skipped (e.g. it provided optional initialisation state), the above allows nil to be passed as the first parameter without overlaying the function to expose pointer parameters.

As such, having a TNil type even if it can only express a single value would appear to be valuable.

Alternatively FPC could arguably benefit from a way of nilling the pointer that implements a var parameter and testing whether a var parameter is nilled: the obvious usage of nil^ and Assigned() doesn't work.

MarkMLl

PascalDragon:

--- Quote from: Warfley on March 12, 2022, 07:46:36 pm ---Not only with the example of nullable from my original post. Take dynamic arrays. You cann assign nil to a dynamic array because of compiler magic, but if you want to create your own dynamic array type, e.g. using managed records, you can't make them nil assignable. This brings this weird disconnect where you the compiler provides features that you could closely emulate, but not fully, because the compiler maigc won't let you. Like if you wanted to extend the dynamic types, string and array, with a dynamic dictionairy or set type, you simply can't because the compiler won't let you create the same features, it allows in other places.
--- End quote ---

And so what? You can't fully duplicate Writeln either.

We simply are not interested in introducing some kind of Nil-type.


--- Quote from: MarkMLl on March 13, 2022, 12:13:39 pm ---Alternatively FPC could arguably benefit from a way of nilling the pointer that implements a var parameter and testing whether a var parameter is nilled: the obvious usage of nil^ and Assigned() doesn't work.

--- End quote ---

One only needs to know how to do it:


--- Code: Pascal  [+][-]window.onload = function(){var x1 = document.getElementById("main_content_section"); if (x1) { var x = document.getElementsByClassName("geshi");for (var i = 0; i < x.length; i++) { x[i].style.maxHeight='none'; x[i].style.height = Math.min(x[i].clientHeight+15,306)+'px'; x[i].style.resize = "vertical";}};} ---procedure Test(var aArg: LongInt);begin  Writeln(HexStr(@aArg));end; var  i: LongInt;begin  Test(i);  Test(PLongInt(Nil)^);end.

Navigation

[0] Message Index

[#] Next page

[*] Previous page

Go to full version