Sysop: | Amessyroom |
---|---|
Location: | Fayetteville, NC |
Users: | 23 |
Nodes: | 6 (0 / 6) |
Uptime: | 49:51:08 |
Calls: | 583 |
Files: | 1,138 |
Messages: | 111,303 |
Build:
$ cc /include=mysql055_root:[include.mysql] /names=as_is demo.c
$ link/share=demo_shr.exe demo + sys$input/opt mysql055_root:[lib.alpha]libclientlib/lib
mysql055_root:[lib.alpha]libsql/lib
mysql055_root:[lib.alpha]libmysys/lib
mysql055_root:[lib.alpha]libdbug/lib
mysql055_root:[lib.alpha]libstrings/lib
mysql055_root:[lib.alpha]libvio/lib
mysql055_root:[lib.alpha]libz/lib
mysql055_root:[lib.alpha]ssl_libssl32/lib mysql055_root:[lib.alpha]ssl_libcrypto32/lib
CASE_SENSITIVE=YES
SYMBOL_VECTOR=(demo_init=PROCEDURE, -
-a-a-a-a-a-a-a-a-a-a-a-a-a-a demo=PROCEDURE, -
-a-a-a-a-a-a-a-a-a-a-a-a-a-a demo_deinit=PROCEDURE)
$
mysql055_root:[lib.alpha]libclientlib/lib
mysql055_root:[lib.alpha]libsql/lib
mysql055_root:[lib.alpha]libmysys/lib
mysql055_root:[lib.alpha]libdbug/lib
mysql055_root:[lib.alpha]libstrings/lib
mysql055_root:[lib.alpha]libvio/lib
mysql055_root:[lib.alpha]libz/lib
mysql055_root:[lib.alpha]ssl_libssl32/lib mysql055_root:[lib.alpha]ssl_libcrypto32/lib
On Tue, 12 Aug 2025 19:08:51 -0400, Arne Vajh|+j wrote:
mysql055_root:[lib.alpha]libclientlib/lib
mysql055_root:[lib.alpha]libsql/lib
mysql055_root:[lib.alpha]libmysys/lib
mysql055_root:[lib.alpha]libdbug/lib
mysql055_root:[lib.alpha]libstrings/lib
mysql055_root:[lib.alpha]libvio/lib
mysql055_root:[lib.alpha]libz/lib
mysql055_root:[lib.alpha]ssl_libssl32/lib
mysql055_root:[lib.alpha]ssl_libcrypto32/lib
Is there some equivalent to rCL-L-2dir-+rCY to add a common directory to a linker search path so you can just shorten most of that to something
more like rCL-lclientlib -lsql -lmysys -ldbug -lstrings -lvio -lzrCY?
On 8/12/2025 11:09 PM, Lawrence D'Oliveiro wrote:
Is there some equivalent to rCL-L-2dir-+rCY to add a common directory to a >> linker search path so you can just shorten most of that to something
more like rCL-lclientlib -lsql -lmysys -ldbug -lstrings -lvio -lzrCY?
VMS is not *nix.
Code:
#include <string.h>
#include <mysql.h>
my_bool demo_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
{
if(args->arg_count == 2 && args->arg_type[0] == STRING_RESULT && args->arg_type[1] == INT_RESULT)
{
return 0;
}
else
{
strcpy(message, "demo function requires two arguments: one
string and one integer");
return 1;
}
}
long long demo(UDF_INIT *initid, UDF_ARGS *args, char *result, unsigned
long *length, unsigned char *is_null, unsigned char *error)
{
const char *sv = args->args[0];
long long iv = *((long long *)args->args[1]);
return strlen(sv) + iv;
}
void demo_deinit(UDF_INIT *initid)
{
}
Build:
$ cc /include=mysql055_root:[include.mysql] /names=as_is demo.c
$ link/share=demo_shr.exe demo + sys$input/opt mysql055_root:[lib.alpha]libclientlib/lib
mysql055_root:[lib.alpha]libsql/lib
mysql055_root:[lib.alpha]libmysys/lib
mysql055_root:[lib.alpha]libdbug/lib
mysql055_root:[lib.alpha]libstrings/lib
mysql055_root:[lib.alpha]libvio/lib
mysql055_root:[lib.alpha]libz/lib
mysql055_root:[lib.alpha]ssl_libssl32/lib mysql055_root:[lib.alpha]ssl_libcrypto32/lib
CASE_SENSITIVE=YES
SYMBOL_VECTOR=(demo_init=PROCEDURE, -
demo=PROCEDURE, -
demo_deinit=PROCEDURE)
$
Install (DCL):
$ copy/log demo_shr.exe mysql055_root:[plugin.alpha]*.*
$ def/sys demo_shr "''f$parse("mysql055_root:[plugin.alpha]demo_shr.exe",,,,"NO_CONCEAL")'"
Install (SQL):
CREATE FUNCTION demo
RETURNS INTEGER
SONAME 'demo_shr';
Demo:
MariaDB [test]> select demo('ABC', 1);
+----------------+
| demo('ABC', 1) |
+----------------+
| 4 |
+----------------+
1 row in set (0.01 sec)
MariaDB [test]> select demo('ABCD', 1);
+-----------------+
| demo('ABCD', 1) |
+-----------------+
| 5 |
+-----------------+
1 row in set (0.00 sec)
MariaDB [test]> select demo('ABC', 2);
+----------------+
| demo('ABC', 2) |
+----------------+
| 5 |
+----------------+
1 row in set (0.00 sec)
MariaDB [test]> SELECT demo();
ERROR 1123 (HY000): Can't initialize function 'demo'; demo function
requires two arguments: one string and one integer
MariaDB [test]> SELECT demo('ABC');
ERROR 1123 (HY000): Can't initialize function 'demo'; demo function
requires two arguments: one string and one integer
MariaDB [test]> SELECT demo('ABC', 'DEF');
ERROR 1123 (HY000): Can't initialize function 'demo'; demo function
requires two arguments: one string and one integer
MariaDB [test]> SELECT demo('ABC', 1, 1);
ERROR 1123 (HY000): Can't initialize function 'demo'; demo function
requires two arguments: one string and one integer
Arne
On 2025-08-12, Arne Vajh|+j <arne@vajhoej.dk> wrote:
Code:
#include <string.h>
#include <mysql.h>
my_bool demo_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
{
if(args->arg_count == 2 && args->arg_type[0] == STRING_RESULT &&
args->arg_type[1] == INT_RESULT)
Is it guaranteed that arg_type[] will always have at least elements ?
If not, that's dangerous unless the compiler you are using does
expression short-circuiting.
{
return 0;
}
else
{
strcpy(message, "demo function requires two arguments: one
string and one integer");
return 1;
YUCK!!! :-) Does MySQL provide a maximum error message size field or
constant that you can use with strncpy() instead ?
On 8/15/2025 8:27 AM, Simon Clubley wrote:
On 2025-08-12, Arne Vajh|+j <arne@vajhoej.dk> wrote:
Code:
#include <string.h>
#include <mysql.h>
my_bool demo_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
{
-a-a-a-a-a if(args->arg_count == 2 && args->arg_type[0] == STRING_RESULT && >>> args->arg_type[1] == INT_RESULT)
Is it guaranteed that arg_type[] will always have at least elements ?
If not, that's dangerous unless the compiler you are using does
expression short-circuiting.
Isn't C required to do short circuiting on && ?
-a-a-a-a-a {
-a-a-a-a-a-a-a-a-a return 0;
-a-a-a-a-a }
-a-a-a-a-a else
-a-a-a-a-a {
-a-a-a-a-a-a-a-a-a strcpy(message, "demo function requires two arguments: one
string and one integer");
-a-a-a-a-a-a-a-a-a return 1;
YUCK!!! :-) Does MySQL provide a maximum error message size field or
constant that you can use with strncpy() instead ?
Not that I am aware of.
No such used in the example provided by MySQL/Oracle.
Arne
On 2025-08-12, Arne Vajhoj <arne@vajhoej.dk> wrote:
Code:
#include <string.h>
#include <mysql.h>
my_bool demo_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
{
if(args->arg_count == 2 && args->arg_type[0] == STRING_RESULT &&
args->arg_type[1] == INT_RESULT)
Is it guaranteed that arg_type[] will always have at least elements ?
If not, that's dangerous unless the compiler you are using does
expression short-circuiting.
{
return 0;
}
else
{
strcpy(message, "demo function requires two arguments: one
string and one integer");
return 1;
YUCK!!! :-) Does MySQL provide a maximum error message size field or
constant that you can use with strncpy() instead ?
On 8/15/2025 9:35 AM, Arne Vajh|+j wrote:^not> an AND_THEN and OR_ELSE operator much like you find
On 8/15/2025 8:27 AM, Simon Clubley wrote:
On 2025-08-12, Arne Vajh|+j <arne@vajhoej.dk> wrote:
Code:
#include <string.h>
#include <mysql.h>
my_bool demo_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
{
-a-a-a-a-a if(args->arg_count == 2 && args->arg_type[0] == STRING_RESULT &&
args->arg_type[1] == INT_RESULT)
Is it guaranteed that arg_type[] will always have at least elements ?
If not, that's dangerous unless the compiler you are using does
expression short-circuiting.
Isn't C required to do short circuiting on && ?
Yes, C and C++ short-circuits.-a Other languages may not.-a For example, Pascal does promise short-circuit which is why our Pascal also provides
In article <107n93n$13rjm$1@dont-email.me>,
Simon Clubley <clubley@remove_me.eisner.decus.org-Earth.UFP> wrote:
On 2025-08-12, Arne Vajhoj <arne@vajhoej.dk> wrote:
Code:
#include <string.h>
#include <mysql.h>
my_bool demo_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
{
if(args->arg_count == 2 && args->arg_type[0] == STRING_RESULT &&
args->arg_type[1] == INT_RESULT)
Is it guaranteed that arg_type[] will always have at least elements ?
If not, that's dangerous unless the compiler you are using does
expression short-circuiting.
C is well-defined in this regard. Boolean expressions in C,
created by combining logical subexpressions with the `&&` and
`||` operators, are documented to use short-circuiting behavior.
However, I must disagree strongly with the advice to use
`strncpy`, which is poorly understood and has strange semantics:
it will write as much of the source string to the destination as
it can, with or without the NUL terminating byte. If the source
is smaller than the destination buffer, then the remainder of
the buffer will be filled with 0s. If the source is exactly as
long as, or longer, than the destination, then the destination
will not be NUL-terminated. Since it just returns the
destination pointer, there is no way to detect truncation other
than to test the last byte in the destination to see whether it
is zero or not. So it is inefficent in the common case, and
dangerous and awkward in the exceptional case. Moreover, its
behavior is orthogonal to that of `strncat`, which does _not_
have the "write 0s to all bytes in the destination past the end
of the what we copied from the source string", and is also
awkward in how it treats it's length argument: whereas for
`strncpy` the length argument is the size of the entire
destination buffer, for `strncat` it is not: `strncat` will
write up to n+1 bytes into the destination.
On 2025-08-15, Dan Cross <cross@spitfire.i.gajendra.net> wrote:
In article <107n93n$13rjm$1@dont-email.me>,
Simon Clubley <clubley@remove_me.eisner.decus.org-Earth.UFP> wrote:
On 2025-08-12, Arne Vajh|+j <arne@vajhoej.dk> wrote:
Code:
#include <string.h>
#include <mysql.h>
my_bool demo_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
{
if(args->arg_count == 2 && args->arg_type[0] == STRING_RESULT && >>>> args->arg_type[1] == INT_RESULT)
Is it guaranteed that arg_type[] will always have at least elements ?
If not, that's dangerous unless the compiler you are using does
expression short-circuiting.
C is well-defined in this regard. Boolean expressions in C,
created by combining logical subexpressions with the `&&` and
`||` operators, are documented to use short-circuiting behavior.
Thank you.
Unless it's explicit in the language syntax itself, and given that
I write code in multiple languages, I have long written code that
assumes implicit[*] short-circuiting is not available.
As such, whether implicit short-circuiting is available or not is
not really that important to me, but I will admit I didn't realise
C had it.
[*] By implicit short-circuiting I mean something that's only defined
in the language standard or implemented in a compiler, instead of some explicit syntax in the language itself to state short-circuiting is available.
However, I must disagree strongly with the advice to use
`strncpy`, which is poorly understood and has strange semantics:
it will write as much of the source string to the destination as
it can, with or without the NUL terminating byte. If the source
is smaller than the destination buffer, then the remainder of
the buffer will be filled with 0s. If the source is exactly as
long as, or longer, than the destination, then the destination
will not be NUL-terminated. Since it just returns the
destination pointer, there is no way to detect truncation other
than to test the last byte in the destination to see whether it
is zero or not. So it is inefficent in the common case, and
dangerous and awkward in the exceptional case. Moreover, its
behavior is orthogonal to that of `strncat`, which does _not_
have the "write 0s to all bytes in the destination past the end
of the what we copied from the source string", and is also
awkward in how it treats it's length argument: whereas for
`strncpy` the length argument is the size of the entire
destination buffer, for `strncat` it is not: `strncat` will
write up to n+1 bytes into the destination.
strncpy() makes more sense when you realise that its original purpose
was to fill fixed-size fields in a record with data and to clear the
rest of the field if the source data was smaller than the field size.
BTW, after using strncpy(), my code always unconditionally places
a 0x00 in the final byte of the buffer "just in case :-)".
Simon.
On 15/08/2025 18:33, Simon Clubley wrote:
strncpy() makes more sense when you realise that its original purpose
was to fill fixed-size fields in a record with data and to clear the
rest of the field if the source data was smaller than the field size.
BTW, after using strncpy(), my code always unconditionally places
a 0x00 in the final byte of the buffer "just in case :-)".
That wouldn't be good if you are filling part of a record!
But I believe most curly bracket languages inherited from C in this
regard.
On 2025-08-15, Dan Cross <cross@spitfire.i.gajendra.net> wrote:
In article <107n93n$13rjm$1@dont-email.me>,
Simon Clubley <clubley@remove_me.eisner.decus.org-Earth.UFP> wrote:
On 2025-08-12, Arne Vajh|+j <arne@vajhoej.dk> wrote:
if(args->arg_count == 2 && args->arg_type[0] == STRING_RESULT && >>>> args->arg_type[1] == INT_RESULT)
Is it guaranteed that arg_type[] will always have at least elements ?
If not, that's dangerous unless the compiler you are using does
expression short-circuiting.
C is well-defined in this regard. Boolean expressions in C,
created by combining logical subexpressions with the `&&` and
`||` operators, are documented to use short-circuiting behavior.
Unless it's explicit in the language syntax itself, and given that
I write code in multiple languages, I have long written code that
assumes implicit[*] short-circuiting is not available.
As such, whether implicit short-circuiting is available or not is
not really that important to me, but I will admit I didn't realise
C had it.
[*] By implicit short-circuiting I mean something that's only defined
in the language standard or implemented in a compiler, instead of some explicit syntax in the language itself to state short-circuiting is available.
In article <107n93n$13rjm$1@dont-email.me>,Ah. There is a constant. Good find.
Simon Clubley <clubley@remove_me.eisner.decus.org-Earth.UFP> wrote:
On 2025-08-12, Arne Vajh|+j <arne@vajhoej.dk> wrote:
strcpy(message, "demo function requires two arguments: one
string and one integer");
return 1;
YUCK!!! :-) Does MySQL provide a maximum error message size field or
constant that you can use with strncpy() instead ?
Indeed yuck, and MySQL _does_ provide a constant that gives
the maximum error message size: `MYSQL_ERRMSG_SIZE`. https://dev.mysql.com/doc/extending-mysql/9.4/en/adding-loadable-function.html
On 8/15/2025 9:40 AM, John Reagan wrote:
On 8/15/2025 9:35 AM, Arne Vajh|+j wrote:-a-a-a-a-a-a-a-a-a-a-a-a-a ^not> an AND_THEN and OR_ELSE operator much like you find
On 8/15/2025 8:27 AM, Simon Clubley wrote:
On 2025-08-12, Arne Vajh|+j <arne@vajhoej.dk> wrote:
Code:
#include <string.h>
#include <mysql.h>
my_bool demo_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
{
-a-a-a-a-a if(args->arg_count == 2 && args->arg_type[0] == STRING_RESULT &&
args->arg_type[1] == INT_RESULT)
Is it guaranteed that arg_type[] will always have at least elements ?
If not, that's dangerous unless the compiler you are using does
expression short-circuiting.
Isn't C required to do short circuiting on && ?
Yes, C and C++ short-circuits.-a Other languages may not.-a For example,
Pascal does promise short-circuit which is why our Pascal also provides
in Ada.
VB.NET has AndAlso and OrElse.
But I believe most curly bracket languages inherited from
C in this regard.
Arne
On 8/15/2025 1:33 PM, Simon Clubley wrote:
On 2025-08-15, Dan Cross <cross@spitfire.i.gajendra.net> wrote:
In article <107n93n$13rjm$1@dont-email.me>,
Simon Clubley-a <clubley@remove_me.eisner.decus.org-Earth.UFP> wrote:
On 2025-08-12, Arne Vajh|+j <arne@vajhoej.dk> wrote:
-a-a-a-a-a if(args->arg_count == 2 && args->arg_type[0] == STRING_RESULT &&
args->arg_type[1] == INT_RESULT)
Is it guaranteed that arg_type[] will always have at least elements ?
If not, that's dangerous unless the compiler you are using does
expression short-circuiting.
C is well-defined in this regard.-a Boolean expressions in C,
created by combining logical subexpressions with the `&&` and
`||` operators, are documented to use short-circuiting behavior.
Unless it's explicit in the language syntax itself, and given that
I write code in multiple languages, I have long written code that
assumes implicit[*] short-circuiting is not available.
As such, whether implicit short-circuiting is available or not is
not really that important to me, but I will admit I didn't realise
C had it.
[*] By implicit short-circuiting I mean something that's only defined
in the language standard or implemented in a compiler, instead of some
explicit syntax in the language itself to state short-circuiting is
available.
In general I like the idea of writing code in a way that does
not require the reader to have memorized ten thousand things from
the language spec.
But I do not consider this a matter of remembering the specific
details about an operator - I consider this a matter of remembering
what operator a symbol represent.
I consider "short circuiting AND" and "non short circuiting AND"
to be two different operators.
And in C then && is the first operator not the second operator.
And understanding what operator each symbol represent is not
detail but core. IMHO.
Arne
BTW, BLISS does not promise short-circuit.-a And in the true BLISS
fashion, most of us use the following macros
-a-a-a-a-a-a-a ! AND_THEN(B1,B2,...Bn) returns TRUE if all of Bi are TRUE.
-a-a-a-a-a-a-a ! Evaluates the Bi left to right and stops on the first false one.
-a-a-a-a-a-a-a !
-a-a-a-a-a-a-a AND_THEN(B)[]=
-a-a-a-a-a-a-a-a-a-a-a %IF %LENGTH EQL 1
-a-a-a-a-a-a-a-a-a-a-a %THEN
-a-a-a-a-a-a-a-a-a-a-a-a-a-a-a (B)
-a-a-a-a-a-a-a-a-a-a-a %ELSE
-a-a-a-a-a-a-a-a-a-a-a-a-a-a-a (IF (B) THEN AND_THEN(%REMAINING) ELSE FALSE)
-a-a-a-a-a-a-a-a-a-a-a %FI %,
-a-a-a-a-a-a-a ! OR_ELSE(B1,B2,...Bn) returns FALSE if all of Bi are FALSE.
-a-a-a-a-a-a-a ! Evaluates the Bi left to right and stops on the first true one.
-a-a-a-a-a-a-a !
-a-a-a-a-a-a-a OR_ELSE(B)[]=
-a-a-a-a-a-a-a-a-a-a-a %IF %LENGTH EQL 1
-a-a-a-a-a-a-a-a-a-a-a %THEN
-a-a-a-a-a-a-a-a-a-a-a-a-a-a-a (B)
-a-a-a-a-a-a-a-a-a-a-a %ELSE
-a-a-a-a-a-a-a-a-a-a-a-a-a-a-a (IF (B) THEN TRUE ELSE OR_ELSE(%REMAINING))
-a-a-a-a-a-a-a-a-a-a-a %FI %,
On 8/15/2025 7:48 PM, Arne Vajh|+j wrote:
On 8/15/2025 1:33 PM, Simon Clubley wrote:
On 2025-08-15, Dan Cross <cross@spitfire.i.gajendra.net> wrote:
In article <107n93n$13rjm$1@dont-email.me>,
Simon Clubley-a <clubley@remove_me.eisner.decus.org-Earth.UFP> wrote: >>>>> On 2025-08-12, Arne Vajh|+j <arne@vajhoej.dk> wrote:
-a-a-a-a-a if(args->arg_count == 2 && args->arg_type[0] ==
STRING_RESULT &&
args->arg_type[1] == INT_RESULT)
Is it guaranteed that arg_type[] will always have at least elements ? >>>>> If not, that's dangerous unless the compiler you are using does
expression short-circuiting.
C is well-defined in this regard.-a Boolean expressions in C,
created by combining logical subexpressions with the `&&` and
`||` operators, are documented to use short-circuiting behavior.
Unless it's explicit in the language syntax itself, and given that
I write code in multiple languages, I have long written code that
assumes implicit[*] short-circuiting is not available.
As such, whether implicit short-circuiting is available or not is
not really that important to me, but I will admit I didn't realise
C had it.
[*] By implicit short-circuiting I mean something that's only defined
in the language standard or implemented in a compiler, instead of some
explicit syntax in the language itself to state short-circuiting is
available.
In general I like the idea of writing code in a way that does
not require the reader to have memorized ten thousand things from
the language spec.
But I do not consider this a matter of remembering the specific
details about an operator - I consider this a matter of remembering
what operator a symbol represent.
I consider "short circuiting AND" and "non short circuiting AND"
to be two different operators.
BTW, while the C frontend always generates the "short-circuiting" AND
and OR intermediate opcodes, the GEM optimizer works to detect if that
is really needed.-a It is hoping to hoist something from the right-hand
side out of a loop (which happens more than you think) and on Itanium it
can even put both left and right in the same bundle if possible (which doesn't happen all that much)
In general I like the idea of writing code in a way that does not
require the reader to have memorized ten thousand things from the
language spec.
On Fri, 15 Aug 2025 09:55:17 -0400, Arne Vajh|+j wrote:
But I believe most curly bracket languages inherited from C in this
regard.
Python took over the C operator hierarchy, with one subtle little
twist. It slightly tweaked the precedence of the bitwise operators
relative to the comparisons, so you donrCOt need parentheses in
expressions like
(C) (-2val-+ & -2bitmask-+) == -2testvalue-+
(Python) -2val-+ & -2bitmask-+ == -2testvalue-+
I have asked on comp.lang.c whether any existing C code could be
broken by making the same change in that language. In principle it
could, but nobody could come up with any real-world examples.
On Fri, 15 Aug 2025 19:48:14 -0400, Arne Vajh|+j wrote:
In general I like the idea of writing code in a way that does not
require the reader to have memorized ten thousand things from the
language spec.
What language spec has room for ten thousand things in it, anyway?
... oh, Java.
On 8/15/2025 10:22 PM, Lawrence DrCOOliveiro wrote:
On Fri, 15 Aug 2025 19:48:14 -0400, Arne Vajh|+j wrote:
In general I like the idea of writing code in a way that does not
require the reader to have memorized ten thousand things from the
language spec.
What language spec has room for ten thousand things in it, anyway?
... oh, Java.
Language specs for modern languages tend to be pretty big.
On 8/12/2025 11:09 PM, Lawrence D'Oliveiro wrote:
On Tue, 12 Aug 2025 19:08:51 -0400, Arne Vajh|+j wrote:
mysql055_root:[lib.alpha]libclientlib/lib
mysql055_root:[lib.alpha]libsql/lib
mysql055_root:[lib.alpha]libmysys/lib
mysql055_root:[lib.alpha]libdbug/lib
mysql055_root:[lib.alpha]libstrings/lib
mysql055_root:[lib.alpha]libvio/lib
mysql055_root:[lib.alpha]libz/lib
mysql055_root:[lib.alpha]ssl_libssl32/lib
mysql055_root:[lib.alpha]ssl_libcrypto32/lib
Is there some equivalent to rCL-L-2dir-+rCY to add a common directory to a >> linker search path so you can just shorten most of that to something
more like rCL-lclientlib -lsql -lmysys -ldbug -lstrings -lvio -lzrCY?
You can omit location on all libraries except the first and
let the sticky default mechanism add it.
(I don't think that is a nice solution)
You can setup default libraries with LNK$LIBRARY* logicals.
You can create shareable images and stuff all of them into
a shareable library.
On 8/15/25 02:33, Arne Vajh|+j wrote:
On 8/12/2025 11:09 PM, Lawrence D'Oliveiro wrote:...
On Tue, 12 Aug 2025 19:08:51 -0400, Arne Vajh|+j wrote:
mysql055_root:[lib.alpha]libclientlib/lib
mysql055_root:[lib.alpha]libsql/lib
mysql055_root:[lib.alpha]libmysys/lib
mysql055_root:[lib.alpha]libdbug/lib
mysql055_root:[lib.alpha]libstrings/lib
mysql055_root:[lib.alpha]libvio/lib
mysql055_root:[lib.alpha]libz/lib
mysql055_root:[lib.alpha]ssl_libssl32/lib
mysql055_root:[lib.alpha]ssl_libcrypto32/lib
Is there some equivalent to rCL-L-2dir-+rCY to add a common directory to a >>> linker search path so you can just shorten most of that to something
more like rCL-lclientlib -lsql -lmysys -ldbug -lstrings -lvio -lzrCY?
You can omit location on all libraries except the first and
let the sticky default mechanism add it.
(I don't think that is a nice solution)
You may not like it, but using the file specification stickiness or RMS related name context processing is the only useful method to avoid
repeating the directory specification. This works on the command line as well as in option files. And you can have more than one library on a
single option line, anyway.
If you have GNV, you can use its linker wrapper. However, it requires
naming the object libraries in Unix style. Although a "libfoo.olb"
works, there is no way to use an "foo.olb" (and you can't easily get a
full map with cross references). So this will not work for ssl_* in the shown link command. Yeah, you can create (symbolic) links ...
You can setup default libraries with LNK$LIBRARY* logicals.
In your example you would need 9 logicals: LNK$LIBRARY,
LNK$LIBRARY_1, ..., LNK$LIBRARY_8. There is no _0 and-a they must all be defined. The suffixes must start with 1 and must not have a gap in numbering. You can't use a search list. Additionally, the link command
line doesn't show that non-system object libraries are used at all.
You can create shareable images and stuff all of them into
a shareable library.
Then the resulting image or application is no longer "statically"
linked: you need the shareable image at runtime. You have to create a shareable with as many universal symbols, aka symbol vector entries, as global symbols in the libraries - just to avoid specifying a couple of
file paths in the link command.
On 8/17/2025 11:24 AM, hb0815 wrote:
On 8/15/25 02:33, Arne Vajh|+j wrote:
On 8/12/2025 11:09 PM, Lawrence D'Oliveiro wrote:...
On Tue, 12 Aug 2025 19:08:51 -0400, Arne Vajh|+j wrote:
mysql055_root:[lib.alpha]libclientlib/lib
mysql055_root:[lib.alpha]libsql/lib
mysql055_root:[lib.alpha]libmysys/lib
mysql055_root:[lib.alpha]libdbug/lib
mysql055_root:[lib.alpha]libstrings/lib
mysql055_root:[lib.alpha]libvio/lib
mysql055_root:[lib.alpha]libz/lib
mysql055_root:[lib.alpha]ssl_libssl32/lib
mysql055_root:[lib.alpha]ssl_libcrypto32/lib
Is there some equivalent to rCL-L-2dir-+rCY to add a common directory to a >>>> linker search path so you can just shorten most of that to something
more like rCL-lclientlib -lsql -lmysys -ldbug -lstrings -lvio -lzrCY?
You can omit location on all libraries except the first and
let the sticky default mechanism add it.
(I don't think that is a nice solution)
You may not like it, but using the file specification stickiness or
RMS related name context processing is the only useful method to avoid
repeating the directory specification. This works on the command line
as well as in option files. And you can have more than one library on
a single option line, anyway.
It can be used.
But if someone edit the list and either remove libraries or
add libraries, then it is pretty easy to mess up.
If you have GNV, you can use its linker wrapper. However, it requires
naming the object libraries in Unix style. Although a "libfoo.olb"
works, there is no way to use an "foo.olb" (and you can't easily get a
full map with cross references). So this will not work for ssl_* in
the shown link command. Yeah, you can create (symbolic) links ...
I did not even consider GNV.
You can setup default libraries with LNK$LIBRARY* logicals.
In your example you would need 9 logicals: LNK$LIBRARY,
LNK$LIBRARY_1, ..., LNK$LIBRARY_8. There is no _0 and-a they must all
be defined. The suffixes must start with 1 and must not have a gap in
numbering. You can't use a search list. Additionally, the link command
line doesn't show that non-system object libraries are used at all.
It is an option that I considered relevant for the question on
how to shorten link commands.
I would not use it in this case.
As an old Fortran programmer then I find it quite natural that
it starts with _1 and not _0.
:-)
You can create shareable images and stuff all of them into
a shareable library.
Then the resulting image or application is no longer "statically"
linked: you need the shareable image at runtime. You have to create a
shareable with as many universal symbols, aka symbol vector entries,
as global symbols in the libraries - just to avoid specifying a couple
of file paths in the link command.
There is no free lunch.
It is an option for the question on how to shorten link commands.
I would not use it in this case either.
I don't even think I have ever created such a shareable library. But
everyone is using one (IMAGELIB).
Arne
It is an option for the question on how to shorten link commands.
I would not use it in this case either.
I don't even think I have ever created such a shareable library. But
everyone is using one (IMAGELIB).
Can you not use make, MMK (or equiv) utility?
On 8/15/2025 6:42 PM, Lawrence D?Oliveiro wrote:
On Fri, 15 Aug 2025 09:55:17 -0400, Arne Vajhoj wrote:
But I believe most curly bracket languages inherited from C in this
regard.
Python took over the C operator hierarchy, with one subtle little
twist. It slightly tweaked the precedence of the bitwise operators
relative to the comparisons, so you don?t need parentheses in
expressions like
(C) (2val+ & 2bitmask+) == 2testvalue+
(Python) 2val+ & 2bitmask+ == 2testvalue+
I have asked on comp.lang.c whether any existing C code could be
broken by making the same change in that language. In principle it
could, but nobody could come up with any real-world examples.
What about:
if(reperr & sys$put(&rab, 0, 0) != RMS$_NORMAL)
{
printf("Houston we have a problem\n");
}
In general I like the idea of writing code in a way that does
not require the reader to have memorized ten thousand things from
the language spec.
But I do not consider this a matter of remembering the specific
details about an operator - I consider this a matter of remembering
what operator a symbol represent.
I consider "short circuiting AND" and "non short circuiting AND"
to be two different operators.
And in C then && is the first operator not the second operator.
And understanding what operator each symbol represent is not
detail but core. IMHO.
On 2025-08-16, Arne Vajh|+j <arne@vajhoej.dk> wrote:
On 8/15/2025 6:42 PM, Lawrence D?Oliveiro wrote:
On Fri, 15 Aug 2025 09:55:17 -0400, Arne Vajh|+j wrote:
But I believe most curly bracket languages inherited from C in this
regard.
Python took over the C operator hierarchy, with one subtle little
twist. It slightly tweaked the precedence of the bitwise operators
relative to the comparisons, so you don?t need parentheses in
expressions like
(C) (-2val-+ & -2bitmask-+) == -2testvalue-+
(Python) -2val-+ & -2bitmask-+ == -2testvalue-+
I have asked on comp.lang.c whether any existing C code could be
broken by making the same change in that language. In principle it
could, but nobody could come up with any real-world examples.
What about:
if(reperr & sys$put(&rab, 0, 0) != RMS$_NORMAL)
{
printf("Houston we have a problem\n");
}
And it's crap like that which means I tend to ignore operator precedence
and place all subexpressions in brackets (nested if needed).
It avoids stuff like this and makes it _extremely_ clear in the code
what the intention is (and makes it easier to read BTW).
On 2025-08-15, Arne Vajh|+j <arne@vajhoej.dk> wrote:
In general I like the idea of writing code in a way that does
not require the reader to have memorized ten thousand things from
the language spec.
But I do not consider this a matter of remembering the specific
details about an operator - I consider this a matter of remembering
what operator a symbol represent.
I consider "short circuiting AND" and "non short circuiting AND"
to be two different operators.
They are not. One is a subset of the other and both carry out the
same core operation.
And in C then && is the first operator not the second operator.
And understanding what operator each symbol represent is not
detail but core. IMHO.
I disagree. Strongly. Both operators do exactly the same thing which
is to implement a logical AND. Code written using this operator
generates exactly the same logical AND result regardless of whether
short circuiting is in use or not.
In addition however, a short circuiting compiler generates code to
stop evaluation if the previous logical AND subexpression was false.
This is a feature of the compiler and does not turn logical AND into something which does something other than logical AND.
It is _always_ safe to write code which assumes short circuiting is
not in use and it will work exactly the same even in the presence
of a compiler which generates short circuiting code.
It's all about writing robust code, not clever code. My approach
generates much more robust code, especially when you might translate
the code to another language that does not implement short circuiting
and you don't realise this during the translation.
On 8/18/2025 8:37 AM, Simon Clubley wrote:And some languages have both operators.
On 2025-08-15, Arne Vajh|+j <arne@vajhoej.dk> wrote:
In general I like the idea of writing code in a way that does
not require the reader to have memorized ten thousand things from
the language spec.
But I do not consider this a matter of remembering the specific
details about an operator - I consider this a matter of remembering
what operator a symbol represent.
I consider "short circuiting AND" and "non short circuiting AND"
to be two different operators.
They are not. One is a subset of the other and both carry out the
same core operation.
And in C then && is the first operator not the second operator.
And understanding what operator each symbol represent is not
detail but core. IMHO.
I disagree. Strongly. Both operators do exactly the same thing which
is to implement a logical AND. Code written using this operator
generates exactly the same logical AND result regardless of whether
short circuiting is in use or not.
In addition however, a short circuiting compiler generates code to
stop evaluation if the previous logical AND subexpression was false.
This is a feature of the compiler and does not turn logical AND into
something which does something other than logical AND.
Considering two operators the same because the functionality of one is
a subset of the functionality of the other seems unlogical to me.
On 8/18/2025 8:37 AM, Simon Clubley wrote:
It is _always_ safe to write code which assumes short circuiting is
not in use and it will work exactly the same even in the presence
of a compiler which generates short circuiting code.
Not true.
Not if the second expression has side effects.
I am sure that you don't want expressions with side effect. But
it happens.
On 2025-08-15, Dan Cross <cross@spitfire.i.gajendra.net> wrote:
In article <107n93n$13rjm$1@dont-email.me>,
Simon Clubley <clubley@remove_me.eisner.decus.org-Earth.UFP> wrote:
On 2025-08-12, Arne Vajhoj <arne@vajhoej.dk> wrote:
Code:
#include <string.h>
#include <mysql.h>
my_bool demo_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
{
if(args->arg_count == 2 && args->arg_type[0] == STRING_RESULT && >>>> args->arg_type[1] == INT_RESULT)
Is it guaranteed that arg_type[] will always have at least elements ?
If not, that's dangerous unless the compiler you are using does >>>expression short-circuiting.
C is well-defined in this regard. Boolean expressions in C,
created by combining logical subexpressions with the `&&` and
`||` operators, are documented to use short-circuiting behavior.
Thank you.
Unless it's explicit in the language syntax itself, and given that
I write code in multiple languages, I have long written code that
assumes implicit[*] short-circuiting is not available.
As such, whether implicit short-circuiting is available or not is
not really that important to me, but I will admit I didn't realise
C had it.
[*] By implicit short-circuiting I mean something that's only defined
in the language standard or implemented in a compiler, instead of some >explicit syntax in the language itself to state short-circuiting is >available.
However, I must disagree strongly with the advice to use
`strncpy`, which is poorly understood and has strange semantics:
it will write as much of the source string to the destination as
it can, with or without the NUL terminating byte. If the source
is smaller than the destination buffer, then the remainder of
the buffer will be filled with 0s. If the source is exactly as
long as, or longer, than the destination, then the destination
will not be NUL-terminated. Since it just returns the
destination pointer, there is no way to detect truncation other
than to test the last byte in the destination to see whether it
is zero or not. So it is inefficent in the common case, and
dangerous and awkward in the exceptional case. Moreover, its
behavior is orthogonal to that of `strncat`, which does _not_
have the "write 0s to all bytes in the destination past the end
of the what we copied from the source string", and is also
awkward in how it treats it's length argument: whereas for
`strncpy` the length argument is the size of the entire
destination buffer, for `strncat` it is not: `strncat` will
write up to n+1 bytes into the destination.
strncpy() makes more sense when you realise that its original purpose
was to fill fixed-size fields in a record with data and to clear the
rest of the field if the source data was smaller than the field size.
BTW, after using strncpy(), my code always unconditionally places
a 0x00 in the final byte of the buffer "just in case :-)".
On 8/15/2025 10:22 PM, Lawrence DrCOOliveiro wrote:
On Fri, 15 Aug 2025 19:48:14 -0400, Arne Vajh|+j wrote:
In general I like the idea of writing code in a way that does not
require the reader to have memorized ten thousand things from the
language spec.
What language spec has room for ten thousand things in it, anyway?
... oh, Java.
Language specs for modern languages tend to be pretty big.
Java 21 is 872 pages (no library)
C 23 is 761 pages (basic library)
C++ 11 is 1334 pages (basic library)
Fortran 2018 is 646 pages (basic library)
Cobol 2014 is 923 pages (basic library)
Ada 2012 is 951 pages (basic library)
C# 6.0 is 639 pages (no library)
On 8/18/2025 8:37 AM, Simon Clubley wrote:
It's all about writing robust code, not clever code. My approach
generates much more robust code, especially when you might translate
the code to another language that does not implement short circuiting
and you don't realise this during the translation.
I agree with the philosophy in general.
But I have little faith in trying to translate from one language
to another language without deep understanding of operators in the
two languages.
On 8/18/2025 3:42 PM, Arne Vajh|+j wrote:
On 8/18/2025 8:37 AM, Simon Clubley wrote:
It's all about writing robust code, not clever code. My approach
generates much more robust code, especially when you might translate
the code to another language that does not implement short circuiting
and you don't realise this during the translation.
I agree with the philosophy in general.
But I have little faith in trying to translate from one language
to another language without deep understanding of operators in the
two languages.
As warning:
$ type op.c
#include <stdio.h>
int main(int argc, char *argv[])
{
int iv = 5;
printf("%d %d\n", iv / 2, iv % 2);
return 0;
}
$ cc op
$ link op
$ run op
2 1
$ type op.pas
program op(input,output);
var
iv : integer;
begin
iv := 5;
writeln(iv / 2, ' ', iv mod 2);
end.
$ pas op
$ lin op
$ run op
2.50000E+00 1
$ type op.for
program op
integer*4 iv
iv = 5
write(*,*) iv / 2, iv mod 2
end
$ for op
$ lin op
$ run op
2 0
In article <68a3b334$0$713$14726298@news.sunsite.dk>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
On 8/18/2025 3:42 PM, Arne Vajh|+j wrote:
On 8/18/2025 8:37 AM, Simon Clubley wrote:
It's all about writing robust code, not clever code. My approach
generates much more robust code, especially when you might translate
the code to another language that does not implement short circuiting
and you don't realise this during the translation.
I agree with the philosophy in general.
But I have little faith in trying to translate from one language
to another language without deep understanding of operators in the
two languages.
As warning:
$ cc op
$ link op
$ run op
2 1
$ pas op
$ lin op
$ run op
2.50000E+00 1
Of course. In pascal, integer division is spelled, `div`, not
`/`. Why would one expect otherwise?
$ for op
$ lin op
$ run op
2 0
Here, FORTRAN has type promotion rules that require one of the
operands of the `/` binary operator to be of a real type before
the operation is performed as a real. iv/2.0 would give the
floating point result, for FORTRAN-77 and later.
And of course, `iv mod 2` should be, `mod(iv, 2)`.
Should one use parentheses to specify evaluation explicit instead of
relying on operator precedence?
I do think so.
Even if the operator precedence seems clear to you, it might not be
to othersrCoyou shouldnrCOt assume that other programmers know
precedence as well as you do.
On Mon, 18 Aug 2025 15:21:07 -0400, Arne Vajh|+j wrote:
Should one use parentheses to specify evaluation explicit instead of
relying on operator precedence?
I do think so.
Parentheses are best used lightly -- where needed, maybe a little bit more than that, and thatrCOs it.
Otherwise parenthesis clutter introduces its own obstacles to readability.
Even if the operator precedence seems clear to you, it might not be
to othersrCoyou shouldnrCOt assume that other programmers know
precedence as well as you do.
I assume that they are just as able to read the spec as you are.
C += vs C =
PHP == vs PHP ===
printf("%d %d\n", iv / 2, iv % 2);
On Mon, 18 Aug 2025 15:42:49 -0400, Arne Vajh|+j wrote:
C += vs C =
Inconsistency: if rCL==rCY is equality comparison, and rCL!rCY denotes logical
negation, why isnrCOt the inequality operator rCL!==rCY? Because rCL!=rCY looks like
it follows the pattern of rCLa -2op-+= brCY being a short form for rCLa = a -2op-+
brCY.
PHP == vs PHP ===
Why do PHP and Java need the separate rCL===rCY operator in addition to rCL==rCY,
when Python does not?
On 8/18/2025 7:45 PM, Lawrence DrCOOliveiro wrote:
On Mon, 18 Aug 2025 15:21:07 -0400, Arne Vajh|+j wrote:
Should one use parentheses to specify evaluation explicit instead of
relying on operator precedence?
I do think so.
Parentheses are best used lightly -- where needed, maybe a little bit
more than that, and thatrCOs it.
Otherwise parenthesis clutter introduces its own obstacles to
readability.
That is not the mantra among people who try to prevent future errors.
Even if the operator precedence seems clear to you, it might not be to
othersrCoyou shouldnrCOt assume that other programmers know precedence as >>> well as you do.
I assume that they are just as able to read the spec as you are.
able to <> will
Is it OK for a language to change operator precedence, because the
change would only make a difference for code not following good
style?
I don't think so.
Changing behavior of existing code is not acceptable. Not even
for bad style code.
I know a few languages has made such changes (changing behavior of
existing code - not specifically changing operator precedence).
But I still don't like it.
On Mon, 18 Aug 2025 19:11:48 -0400, Arne Vajh|+j wrote:
printf("%d %d\n", iv / 2, iv % 2);
The interpretation in C of rCL/rCY being an integer operation with integer operands, and float otherwise, is generally regarded as a Bad Idea. I
think it caught the infection from Fortran.
Python actually started out following this interpretation, then changed to always returning a float, introducing the additional separate rCL//rCY operator for when you explicitly want integer division.
Even PHP, bad as it is in other ways, did not follow the C mistake.
PS: Yes - both Scala 2.13 and 3.3 runs fine on VMS. For 3.3 source files
-a-a-a must be rfm:stmlf.
On 8/18/2025 7:27 PM, Dan Cross wrote:
In article <68a3b334$0$713$14726298@news.sunsite.dk>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
On 8/18/2025 3:42 PM, Arne Vajh|+j wrote:
On 8/18/2025 8:37 AM, Simon Clubley wrote:
It's all about writing robust code, not clever code. My approach
generates much more robust code, especially when you might translate >>>>> the code to another language that does not implement short circuiting >>>>> and you don't realise this during the translation.
I agree with the philosophy in general.
But I have little faith in trying to translate from one language
to another language without deep understanding of operators in the
two languages.
As warning:
$ cc op
$ link op
$ run op
2 1
$ pas op
$ lin op
$ run op
2.50000E+00 1
Of course. In pascal, integer division is spelled, `div`, not
`/`. Why would one expect otherwise?
$ for op
$ lin op
$ run op
2 0
Here, FORTRAN has type promotion rules that require one of the
operands of the `/` binary operator to be of a real type before
the operation is performed as a real. iv/2.0 would give the
floating point result, for FORTRAN-77 and later.
And of course, `iv mod 2` should be, `mod(iv, 2)`.
Yes.
But point is that one need to know something about the
languages.
Just picking an operator that "looks like" and hope it
has similar semantics is no good.
In article <68a3b980$0$713$14726298@news.sunsite.dk>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
But point is that one need to know something about the
languages.
Just picking an operator that "looks like" and hope it
has similar semantics is no good.
This seems like a very extreme example. There is a scale of
knowledge when it comes to programming languages, from the basic
ways in which one does various things like write loops or
perform basic arithmetic, to the minutia of specific library or
IO routines, with semantics of specific operators and how they
combine probably somewhere in the middle.
I happen to disagree with Simon's notion of what makes for
robust programming, but to go to such an extreme as to suggest
that writing code as if logical operators don't short-circuit
is the same as not knowing the semantics of division is
specious.
I agree that the risk of someone not understanding "division"
ways is much less than the risk of someone not understanding "and" ways.
On Mon, 18 Aug 2025 19:48:16 -0400, Arne Vajh|+j wrote:
On 8/18/2025 7:45 PM, Lawrence DrCOOliveiro wrote:
On Mon, 18 Aug 2025 15:21:07 -0400, Arne Vajh|+j wrote:
Should one use parentheses to specify evaluation explicit instead of
relying on operator precedence?
I do think so.
Parentheses are best used lightly -- where needed, maybe a little bit
more than that, and thatrCOs it.
Otherwise parenthesis clutter introduces its own obstacles to
readability.
That is not the mantra among people who try to prevent future errors.
There are people who just repeat what they are told, arenrCOt there, instead of learning from actual experience.
On 8/18/2025 7:59 PM, Lawrence DrCOOliveiro wrote:
On Mon, 18 Aug 2025 19:48:16 -0400, Arne Vajh|+j wrote:
On 8/18/2025 7:45 PM, Lawrence DrCOOliveiro wrote:
Parentheses are best used lightly -- where needed, maybe a little
bit more than that, and thatrCOs it.
Otherwise parenthesis clutter introduces its own obstacles to
readability.
That is not the mantra among people who try to prevent future
errors.
There are people who just repeat what they are told, arenrCOt there,
instead of learning from actual experience.
It is the recommendation from people with actual experience.
One book that recommend it is "The Practice of Programming".
Brian Kernighan and Rob Pike.
On 8/18/2025 8:48 PM, Dan Cross wrote:
In article <68a3b980$0$713$14726298@news.sunsite.dk>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
But point is that one need to know something about the
languages.
Just picking an operator that "looks like" and hope it
has similar semantics is no good.
This seems like a very extreme example. There is a scale of
knowledge when it comes to programming languages, from the basic
ways in which one does various things like write loops or
perform basic arithmetic, to the minutia of specific library or
IO routines, with semantics of specific operators and how they
combine probably somewhere in the middle.
I happen to disagree with Simon's notion of what makes for
robust programming, but to go to such an extreme as to suggest
that writing code as if logical operators don't short-circuit
is the same as not knowing the semantics of division is
specious.
There are 4 operations:
- short circuiting and
- non short circuiting and
- integer division
- floating point division
Both source and target language has a way of doing those: operator,
function or a more complex expression.
I agree that the risk of someone not understanding "division"
ways is much less than the risk of someone not understanding
"and" ways.
But in the end the team doing the translation need to understand
all operations to do a correct translation.
Considering two operators the same because the functionality of one is
a subset of the functionality of the other seems unlogical to me.
C += vs C =
PHP == vs PHP ===
etc.
It is _always_ safe to write code which assumes short circuiting is
not in use and it will work exactly the same even in the presence
of a compiler which generates short circuiting code.
Not true.
Not if the second expression has side effects.
I am sure that you don't want expressions with side effect. But
it happens.
On 8/18/2025 3:42 PM, Arne Vajhoj wrote:
On 8/18/2025 8:37 AM, Simon Clubley wrote:
It is _always_ safe to write code which assumes short circuiting is
not in use and it will work exactly the same even in the presence
of a compiler which generates short circuiting code.
Not true.
Not if the second expression has side effects.
I am sure that you don't want expressions with side effect. But
it happens.
Function calls is a classic example of potential side
effect, but many languages allow assignments in expressions.
Python 3.8 introduced the walrus operator.
In article <107nr15$18f8f$1@dont-email.me>,
Simon Clubley <clubley@remove_me.eisner.decus.org-Earth.UFP> wrote:
Unless it's explicit in the language syntax itself, and given that
I write code in multiple languages, I have long written code that
assumes implicit[*] short-circuiting is not available.
Huh, interesting. I suppose my take is that I have an
obligation to learn the idioms of a given language, if I am
writing code in that language, and this feels like one that is
useful to know about.
To each their own, I suppose.
Or, better yet, write less C and use safer languages. :-D
But point is that one need to know something about the
languages.
Just picking an operator that "looks like" and hope it
has similar semantics is no good.
Are there any languages invented the last 20 years that does
not do integer division for two integer operands?
I happen to disagree with Simon's notion of what makes for
robust programming, but to go to such an extreme as to suggest
that writing code as if logical operators don't short-circuit
is the same as not knowing the semantics of division is
specious.
On 2025-08-18, Dan Cross <cross@spitfire.i.gajendra.net> wrote:
I happen to disagree with Simon's notion of what makes for
robust programming, but to go to such an extreme as to suggest
that writing code as if logical operators don't short-circuit
is the same as not knowing the semantics of division is
specious.
That last one is an interesting example. I may not care about
short circuiting, but I am _very_ _very_ aware of the combined
unsigned integers and signed integers issues in C expressions. :-(
It also affects how I look at the same issues in other languages.
I've mentioned this before, but I think languages should give you
unsigned integers by default, and you should have to ask for
a signed integer if you really want one.
On 2025-08-18, Dan Cross <cross@spitfire.i.gajendra.net> wrote:
In article <107nr15$18f8f$1@dont-email.me>,
Simon Clubley <clubley@remove_me.eisner.decus.org-Earth.UFP> wrote:
Unless it's explicit in the language syntax itself, and given that
I write code in multiple languages, I have long written code that
assumes implicit[*] short-circuiting is not available.
Huh, interesting. I suppose my take is that I have an
obligation to learn the idioms of a given language, if I am
writing code in that language, and this feels like one that is
useful to know about.
To each their own, I suppose.
I write simple to understand code, not clever code, even when the
problem it is solving is complex or has a lot of functionality
built into the problem.
I've found it makes code more robust and easier for others to read, >especially when they may not have the knowledge you have when you
wrote the original code.
I certainly don't feel the need to write job security code or some
"macho" desire to write dense and hard to understand code to order
to try and demonstrate to others just how "smart" I am.
I am not saying you are doing that BTW, but I've seen enough code
written by others which was clearly written with that mindset.
Or, better yet, write less C and use safer languages. :-D
Unfortunately that's not really possible in many cases. I _strongly_
wish a Wirth-style language had become the standard system integration
and low-level language instead of C.
On Mon, 18 Aug 2025 21:49:29 -0400, Arne Vajh|+j wrote:
On 8/18/2025 7:59 PM, Lawrence DrCOOliveiro wrote:
On Mon, 18 Aug 2025 19:48:16 -0400, Arne Vajh|+j wrote:
On 8/18/2025 7:45 PM, Lawrence DrCOOliveiro wrote:
Parentheses are best used lightly -- where needed, maybe a little
bit more than that, and thatrCOs it.
Otherwise parenthesis clutter introduces its own obstacles to
readability.
That is not the mantra among people who try to prevent future
errors.
There are people who just repeat what they are told, arenrCOt there,
instead of learning from actual experience.
It is the recommendation from people with actual experience.
One book that recommend it is "The Practice of Programming".
Brian Kernighan and Rob Pike.
One wonders how much experience they really have, across how many
different languages.
On 2025-08-18, Arne Vajh|+j <arne@vajhoej.dk> wrote:
On 8/18/2025 3:42 PM, Arne Vajh|+j wrote:
On 8/18/2025 8:37 AM, Simon Clubley wrote:
It is _always_ safe to write code which assumes short circuiting is
not in use and it will work exactly the same even in the presence
of a compiler which generates short circuiting code.
Not true.
Not if the second expression has side effects.
I am sure that you don't want expressions with side effect. But
it happens.
Function calls is a classic example of potential side
effect, but many languages allow assignments in expressions.
Python 3.8 introduced the walrus operator.
Then Python has lost the plot. When you do ugly things like this, then
the easier it is for subtle errors to slip in. Also, you write code once (hopefully), but read it many times.
On 2025-08-18, Dan Cross <cross@spitfire.i.gajendra.net> wrote:
I happen to disagree with Simon's notion of what makes for
robust programming, but to go to such an extreme as to suggest
that writing code as if logical operators don't short-circuit
is the same as not knowing the semantics of division is
specious.
That last one is an interesting example. I may not care about
short circuiting, but I am _very_ _very_ aware of the combined
unsigned integers and signed integers issues in C expressions. :-(
It also affects how I look at the same issues in other languages.
I've mentioned this before, but I think languages should give you
unsigned integers by default, and you should have to ask for
a signed integer if you really want one.
On 2025-08-18, Arne Vajh|+j <arne@vajhoej.dk> wrote:
Are there any languages invented the last 20 years that does
not do integer division for two integer operands?
Javascript's basic number data type is a floating point number. :-(
Make of that what you will and also the mindset of someone who thought
that was a good idea.
Yes, I know Javascript is older than that but it's been through
multiple standards processes.
On 2025-08-18, Arne Vajh|+j <arne@vajhoej.dk> wrote:
It is _always_ safe to write code which assumes short circuiting is
not in use and it will work exactly the same even in the presence
of a compiler which generates short circuiting code.
Not true.
Not if the second expression has side effects.
I am sure that you don't want expressions with side effect. But
it happens.
Tell me Arne, given what you now know about me, do you really think
I would ever write code that had expression side effects like that ? :-)
In article <1081sk3$3njqo$7@dont-email.me>,
Simon Clubley <clubley@remove_me.eisner.decus.org-Earth.UFP> wrote:
On 2025-08-18, Dan Cross <cross@spitfire.i.gajendra.net> wrote:
I happen to disagree with Simon's notion of what makes for
robust programming, but to go to such an extreme as to suggest
that writing code as if logical operators don't short-circuit
is the same as not knowing the semantics of division is
specious.
That last one is an interesting example. I may not care about
short circuiting, but I am _very_ _very_ aware of the combined
unsigned integers and signed integers issues in C expressions. :-(
It also affects how I look at the same issues in other languages.
I've mentioned this before, but I think languages should give you
unsigned integers by default, and you should have to ask for
a signed integer if you really want one.
Whether integers are signed or unsigned by default is not
terribly interesting to me, but I do believe, strongly, that
implicit type conversions as in C are a Bad Idea(TM), and I
think that history has shown that view to be more or less
correct; the only language that seems to get this approximately
right is Haskell, using typeclasses, but that's not implicit
coercion; it takes well-defined, strongly-typed functions that
do explicit conversions internally, from the prelude.
But that's Haskell. For most programming, if one wants to do
arithmetic on operands of differing type, then one should be
required to explicitly convert everything to a single, uniform
type and live with whatever the semantics of that type are.
This needn't be as tedious or verbose as it sounds; with a
little bit of type inference, it can be quite succinct while
still being safe and correct.
On 8/19/2025 10:09 AM, Dan Cross wrote:
In article <1081sk3$3njqo$7@dont-email.me>,
Simon Clubley-a <clubley@remove_me.eisner.decus.org-Earth.UFP> wrote:
On 2025-08-18, Dan Cross <cross@spitfire.i.gajendra.net> wrote:
I happen to disagree with Simon's notion of what makes for
robust programming, but to go to such an extreme as to suggest
that writing code as if logical operators don't short-circuit
is the same as not knowing the semantics of division is
specious.
That last one is an interesting example. I may not care about
short circuiting, but I am _very_ _very_ aware of the combined
unsigned integers and signed integers issues in C expressions. :-(
It also affects how I look at the same issues in other languages.
I've mentioned this before, but I think languages should give you
unsigned integers by default, and you should have to ask for
a signed integer if you really want one.
Whether integers are signed or unsigned by default is not
terribly interesting to me, but I do believe, strongly, that
implicit type conversions as in C are a Bad Idea(TM), and I
think that history has shown that view to be more or less
correct; the only language that seems to get this approximately
right is Haskell, using typeclasses, but that's not implicit
coercion; it takes well-defined, strongly-typed functions that
do explicit conversions internally, from the prelude.
But that's Haskell.-a For most programming, if one wants to do
arithmetic on operands of differing type, then one should be
required to explicitly convert everything to a single, uniform
type and live with whatever the semantics of that type are.
This needn't be as tedious or verbose as it sounds; with a
little bit of type inference, it can be quite succinct while
still being safe and correct.
Kotlin is rather picky about mixing signed and unsigned.
var v: UInt = 16u
v = v / 2
gives an error.
v = v / 2u
v = v / 2.toUInt()
works.
I consider that rather picky.
Arne
On 19/08/2025 16:10, Arne Vajh|+j wrote:
On 8/19/2025 10:09 AM, Dan Cross wrote:programmer making an explicit conversion
Whether integers are signed or unsigned by default is not
terribly interesting to me, but I do believe, strongly, that
implicit type conversions as in C are a Bad Idea(TM), and I
think that history has shown that view to be more or less
correct; the only language that seems to get this approximately
right is Haskell, using typeclasses, but that's not implicit
coercion; it takes well-defined, strongly-typed functions that
do explicit conversions internally, from the prelude.
But that's Haskell.-a For most programming, if one wants to do
arithmetic on operands of differing type, then one should be
required to explicitly convert everything to a single, uniform
type and live with whatever the semantics of that type are.
This needn't be as tedious or verbose as it sounds; with a
little bit of type inference, it can be quite succinct while
still being safe and correct.
Kotlin is rather picky about mixing signed and unsigned.
var v: UInt = 16u
v = v / 2
gives an error.
v = v / 2u
v = v / 2.toUInt()
works.
I consider that rather picky.
Ada as nearly as bad, although that would work, It relies on the
Kotlin is rather picky about mixing signed and unsigned.
var v: UInt = 16u
v = v / 2
gives an error.
v = v / 2u
v = v / 2.toUInt()
works.
I consider that rather picky.
On 8/18/2025 11:00 PM, Lawrence DrCOOliveiro wrote:
On Mon, 18 Aug 2025 21:49:29 -0400, Arne Vajh|+j wrote:
On 8/18/2025 7:59 PM, Lawrence DrCOOliveiro wrote:
On Mon, 18 Aug 2025 19:48:16 -0400, Arne Vajh|+j wrote:
On 8/18/2025 7:45 PM, Lawrence DrCOOliveiro wrote:
Parentheses are best used lightly -- where needed, maybe a little
bit more than that, and thatrCOs it.
Otherwise parenthesis clutter introduces its own obstacles to
readability.
That is not the mantra among people who try to prevent future
errors.
There are people who just repeat what they are told, arenrCOt there,
instead of learning from actual experience.
It is the recommendation from people with actual experience.
One book that recommend it is "The Practice of Programming".
Brian Kernighan and Rob Pike.
One wonders how much experience they really have, across how many
different languages.
Brian Kernighan and Rob Pike? A lot! :-)
On 8/19/2025 10:09 AM, Dan Cross wrote:
In article <1081sk3$3njqo$7@dont-email.me>,
Simon Clubley <clubley@remove_me.eisner.decus.org-Earth.UFP> wrote:
On 2025-08-18, Dan Cross <cross@spitfire.i.gajendra.net> wrote:
I happen to disagree with Simon's notion of what makes for
robust programming, but to go to such an extreme as to suggest
that writing code as if logical operators don't short-circuit
is the same as not knowing the semantics of division is
specious.
That last one is an interesting example. I may not care about
short circuiting, but I am _very_ _very_ aware of the combined
unsigned integers and signed integers issues in C expressions. :-(
It also affects how I look at the same issues in other languages.
I've mentioned this before, but I think languages should give you
unsigned integers by default, and you should have to ask for
a signed integer if you really want one.
Whether integers are signed or unsigned by default is not
terribly interesting to me, but I do believe, strongly, that
implicit type conversions as in C are a Bad Idea(TM), and I
think that history has shown that view to be more or less
correct; the only language that seems to get this approximately
right is Haskell, using typeclasses, but that's not implicit
coercion; it takes well-defined, strongly-typed functions that
do explicit conversions internally, from the prelude.
But that's Haskell. For most programming, if one wants to do
arithmetic on operands of differing type, then one should be
required to explicitly convert everything to a single, uniform
type and live with whatever the semantics of that type are.
This needn't be as tedious or verbose as it sounds; with a
little bit of type inference, it can be quite succinct while
still being safe and correct.
Kotlin is rather picky about mixing signed and unsigned.
var v: UInt = 16u
v = v / 2
gives an error.
v = v / 2u
v = v / 2.toUInt()
works.
I consider that rather picky.
On 8/19/2025 9:01 AM, Simon Clubley wrote:
On 2025-08-18, Dan Cross <cross@spitfire.i.gajendra.net> wrote:
I happen to disagree with Simon's notion of what makes for
robust programming, but to go to such an extreme as to suggest
that writing code as if logical operators don't short-circuit
is the same as not knowing the semantics of division is
specious.
That last one is an interesting example. I may not care about
short circuiting, but I am _very_ _very_ aware of the combined
unsigned integers and signed integers issues in C expressions. :-(
It also affects how I look at the same issues in other languages.
I've mentioned this before, but I think languages should give you
unsigned integers by default, and you should have to ask for
a signed integer if you really want one.
"by default" sort of imply signedness being an attribute of
same type.
Why not just make it two different types with different names?
Whether we follow tradition and call them integer and cardinal
or more modern style and call them int and uint is less important.
In article <10822mn$3pb8v$1@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
On 8/18/2025 11:00 PM, Lawrence DrCOOliveiro wrote:
On Mon, 18 Aug 2025 21:49:29 -0400, Arne Vajh|+j wrote:
On 8/18/2025 7:59 PM, Lawrence DrCOOliveiro wrote:
On Mon, 18 Aug 2025 19:48:16 -0400, Arne Vajh|+j wrote:
On 8/18/2025 7:45 PM, Lawrence DrCOOliveiro wrote:
Parentheses are best used lightly -- where needed, maybe a little >>>>>>> bit more than that, and thatrCOs it.
Otherwise parenthesis clutter introduces its own obstacles to
readability.
That is not the mantra among people who try to prevent future
errors.
There are people who just repeat what they are told, arenrCOt there, >>>>> instead of learning from actual experience.
It is the recommendation from people with actual experience.
One book that recommend it is "The Practice of Programming".
Brian Kernighan and Rob Pike.
One wonders how much experience they really have, across how many
different languages.
(Wow.)
Brian Kernighan and Rob Pike? A lot! :-)
It may help to read what they actually wrote in TPoP; on page 6:
|_Parenthesize to resolve ambiguity_. Parentheses specify
|grouping and can be used to make the intent clear even when
|they are not required. The inner parentheses in the previous
|example are not necessary, but they don't hurt, either.
|Seasoned programmers might omit them, because the relational
|operators (< <= == != >= >) have higher precedence than the
|logical operators (&& and ||).
|
|When mixing unrelated operators, though, it's a good idea to
|parenthesize. C and its friends present pernicious precedence
|problems, and it's easy to make a mistake.
For reference, the "previous example" they mention here is:
if ((block_id >= actblks) || (block_id < unblocks))
Most C programmers would write this as,
if (block_id >= actblks || block_id < unblocks)
And Kernighan and Pike would be fine with that. It must be
noted that, throughout the rest of TPoP, they rarely
parenthesize as aggressively as they do in that one example.
For example, on page 98, in the discussion of building a CSV
file parser interface, they present a function called,
`advquoted` that contains this line of code:
if (pj] == '"' && p[++j] != '"') {
...
}
(Note this doesn't just omit parenthesis, but also makes use of
the pre-increment operator _and_ boolean short-circuiting.)
Pike is famous for brevity; his 1989 document, "Notes on
Programming in C" is a model here: http://www.literateprogramming.com/pikestyle.pdf
Even now, it's still an interesting read. I like my own code
princples, as well, but of course, I'm biased: https://pub.gajendra.net/2016/03/code_principles
- Dan C.
Two points related to the fact that they have a special operator instead
of just using plain assignment.
On 8/18/2025 11:00 PM, Lawrence DrCOOliveiro wrote:
One wonders how much experience they really have, across how many
different languages.
Brian Kernighan and Rob Pike? A lot! :-)
In article <68a493ec$0$710$14726298@news.sunsite.dk>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
Kotlin is rather picky about mixing signed and unsigned.
var v: UInt = 16u
v = v / 2
gives an error.
v = v / 2u
v = v / 2.toUInt()
works.
I consider that rather picky.
It's kind of annoying that it can't infer to use unsigned for
the '2' in the first example. Rust, for example, does do that
inference which makes most arithmetic very natural.
In article <1081rg2$3njqo$3@dont-email.me>,
Simon Clubley <clubley@remove_me.eisner.decus.org-Earth.UFP> wrote:
I write simple to understand code, not clever code, even when the
problem it is solving is complex or has a lot of functionality
built into the problem.
I've found it makes code more robust and easier for others to read, >>especially when they may not have the knowledge you have when you
wrote the original code.
I'm curious how this expresses itself with respect to e.g. the short-circuiting thing, though. For instance, this might be
common in C:
struct something *p;
...
if (p != NULL && p->ptr != NULL && something(*p->ptr)) {
// Do something here.
}
This, of course, relies on short-circuiting to avoid
dereferncing either `p` or `*p->ptr` if either is NULL. What
is the alternative?
if (p != NULL) {
if (p->ptr != NULL) {
if (something(*p->ptr)) {
// Do something....
}
}
}
If I dare say so, this is strictly worse because the code is now
much more heavily indented.
Ken Thompson used to avoid things like this by writing such code
as:
if (p != NULL)
if (p->ptr != NULL)
if (something(p->ptr)) {
// Do something....
}
Which has a certain elegance to it, but automated code
formatters inevitably don't understand it (and at this point,
one really ought to be using an automated formatter whenever
possible).
AN alternative might be to extract the conditional and put it
into an auxiliary function, and use something similar to
Dijkstra's guarded commands:
void
maybe_do_something(struct something *p)
{
if (p == NULL)
return;
if (p->ptr == NULL)
return;
if (!something(*p->ptr))
return;
// Now do something.
}
I would argue that this is better than the previous example, and
possibly on par with or better than the original: if nothing
else, it gives a name to the operation. This is of course just
a contrived example, so the name here is meaningless, but one
hopes that in a real program a name with some semantic meaning
would be chosen.
Even now, it's still an interesting read. I like my own code
princples, as well, but of course, I'm biased: https://pub.gajendra.net/2016/03/code_principles
On 19/08/2025 17:07, Dan Cross wrote:
In article <10822mn$3pb8v$1@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
On 8/18/2025 11:00 PM, Lawrence DrCOOliveiro wrote:
On Mon, 18 Aug 2025 21:49:29 -0400, Arne Vajh|+j wrote:
On 8/18/2025 7:59 PM, Lawrence DrCOOliveiro wrote:
On Mon, 18 Aug 2025 19:48:16 -0400, Arne Vajh|+j wrote:
On 8/18/2025 7:45 PM, Lawrence DrCOOliveiro wrote:
Parentheses are best used lightly -- where needed, maybe a little >>>>>>>> bit more than that, and thatrCOs it.
Otherwise parenthesis clutter introduces its own obstacles to
readability.
That is not the mantra among people who try to prevent future
errors.
There are people who just repeat what they are told, arenrCOt there, >>>>>> instead of learning from actual experience.
It is the recommendation from people with actual experience.
One book that recommend it is "The Practice of Programming".
Brian Kernighan and Rob Pike.
One wonders how much experience they really have, across how many
different languages.
(Wow.)
Brian Kernighan and Rob Pike? A lot! :-)
It may help to read what they actually wrote in TPoP; on page 6:
|_Parenthesize to resolve ambiguity_. Parentheses specify
|grouping and can be used to make the intent clear even when
|they are not required. The inner parentheses in the previous
|example are not necessary, but they don't hurt, either.
|Seasoned programmers might omit them, because the relational
|operators (< <= == != >= >) have higher precedence than the
|logical operators (&& and ||).
|
|When mixing unrelated operators, though, it's a good idea to
|parenthesize. C and its friends present pernicious precedence
|problems, and it's easy to make a mistake.
For reference, the "previous example" they mention here is:
if ((block_id >= actblks) || (block_id < unblocks))
Most C programmers would write this as,
if (block_id >= actblks || block_id < unblocks)
And Kernighan and Pike would be fine with that. It must be
noted that, throughout the rest of TPoP, they rarely
parenthesize as aggressively as they do in that one example.
For example, on page 98, in the discussion of building a CSV
file parser interface, they present a function called,
`advquoted` that contains this line of code:
if (pj] == '"' && p[++j] != '"') {
...
}
(Note this doesn't just omit parenthesis, but also makes use of
the pre-increment operator _and_ boolean short-circuiting.)
Pike is famous for brevity; his 1989 document, "Notes on
Programming in C" is a model here:
http://www.literateprogramming.com/pikestyle.pdf
Even now, it's still an interesting read. I like my own code
princples, as well, but of course, I'm biased:
https://pub.gajendra.net/2016/03/code_principles
- Dan C.
Interestingly I have just come across an old bit of DEC Basic code:
REPORT.ONLY = W.S4 = "R" ! Global flag
I know what it does, but I would wrapped the knuckles of any programmer
who did that on my shift!
In article <1082lks$3nmtt$2@dont-email.me>,
Chris Townley <news@cct-net.co.uk> wrote:
On 19/08/2025 17:07, Dan Cross wrote:
In article <10822mn$3pb8v$1@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
On 8/18/2025 11:00 PM, Lawrence DrCOOliveiro wrote:
On Mon, 18 Aug 2025 21:49:29 -0400, Arne Vajh|+j wrote:
On 8/18/2025 7:59 PM, Lawrence DrCOOliveiro wrote:
On Mon, 18 Aug 2025 19:48:16 -0400, Arne Vajh|+j wrote:
On 8/18/2025 7:45 PM, Lawrence DrCOOliveiro wrote:
Parentheses are best used lightly -- where needed, maybe a little >>>>>>>>> bit more than that, and thatrCOs it.
Otherwise parenthesis clutter introduces its own obstacles to >>>>>>>>> readability.
That is not the mantra among people who try to prevent future
errors.
There are people who just repeat what they are told, arenrCOt there, >>>>>>> instead of learning from actual experience.
It is the recommendation from people with actual experience.
One book that recommend it is "The Practice of Programming".
Brian Kernighan and Rob Pike.
One wonders how much experience they really have, across how many
different languages.
(Wow.)
Brian Kernighan and Rob Pike? A lot! :-)
It may help to read what they actually wrote in TPoP; on page 6:
|_Parenthesize to resolve ambiguity_. Parentheses specify
|grouping and can be used to make the intent clear even when
|they are not required. The inner parentheses in the previous
|example are not necessary, but they don't hurt, either.
|Seasoned programmers might omit them, because the relational
|operators (< <= == != >= >) have higher precedence than the
|logical operators (&& and ||).
|
|When mixing unrelated operators, though, it's a good idea to
|parenthesize. C and its friends present pernicious precedence
|problems, and it's easy to make a mistake.
For reference, the "previous example" they mention here is:
if ((block_id >= actblks) || (block_id < unblocks))
Most C programmers would write this as,
if (block_id >= actblks || block_id < unblocks)
And Kernighan and Pike would be fine with that. It must be
noted that, throughout the rest of TPoP, they rarely
parenthesize as aggressively as they do in that one example.
For example, on page 98, in the discussion of building a CSV
file parser interface, they present a function called,
`advquoted` that contains this line of code:
if (pj] == '"' && p[++j] != '"') {
...
}
(Note this doesn't just omit parenthesis, but also makes use of
the pre-increment operator _and_ boolean short-circuiting.)
Pike is famous for brevity; his 1989 document, "Notes on
Programming in C" is a model here:
http://www.literateprogramming.com/pikestyle.pdf
Even now, it's still an interesting read. I like my own code
princples, as well, but of course, I'm biased:
https://pub.gajendra.net/2016/03/code_principles
- Dan C.
Interestingly I have just come across an old bit of DEC Basic code:
REPORT.ONLY = W.S4 = "R" ! Global flag
I know what it does, but I would wrapped the knuckles of any programmer
who did that on my shift!
Not knowing DEC BASIC, am I correct in guessing that this
assigns the boolean result of comparing `W.S4` with the string
"R" to `REPORT.ONLY`?
- Dan C.
On 2025-08-19, Dan Cross <cross@spitfire.i.gajendra.net> wrote:
Even now, it's still an interesting read. I like my own code
princples, as well, but of course, I'm biased:
https://pub.gajendra.net/2016/03/code_principles
I've just read through that document and agree with everything there.
I was especially amused by the write for readability and it will be
read many times comments as I use that wording myself.
I am surprised you are picking me up on some things however, given
the mindset expressed in that document. Perhaps your idea of readability
is different from mine. :-)
On 2025-08-19, Dan Cross <cross@spitfire.i.gajendra.net> wrote:
In article <68a493ec$0$710$14726298@news.sunsite.dk>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
Kotlin is rather picky about mixing signed and unsigned.
var v: UInt = 16u
v = v / 2
gives an error.
v = v / 2u
v = v / 2.toUInt()
works.
I consider that rather picky.
I've not used Kotlin, but I consider that to be the really good type
of picky. :-)
It's kind of annoying that it can't infer to use unsigned for
the '2' in the first example. Rust, for example, does do that
inference which makes most arithmetic very natural.
I actually consider that to be a good thing. The programmer is forced
to think about what they have written and to change it to make those >intentions explicit in the code. I like this.
On 8/18/2025 8:48 PM, Dan Cross wrote:
In article <68a3b980$0$713$14726298@news.sunsite.dk>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
But point is that one need to know something about the
languages.
Just picking an operator that "looks like" and hope it
has similar semantics is no good.
This seems like a very extreme example. There is a scale of
knowledge when it comes to programming languages, from the basic
ways in which one does various things like write loops or
perform basic arithmetic, to the minutia of specific library or
IO routines, with semantics of specific operators and how they
combine probably somewhere in the middle.
I happen to disagree with Simon's notion of what makes for
robust programming, but to go to such an extreme as to suggest
that writing code as if logical operators don't short-circuit
is the same as not knowing the semantics of division is
specious.
There are 4 operations:
- short circuiting and
- non short circuiting and
- integer division
- floating point division
Both source and target language has a way of doing those: operator,
function or a more complex expression.
I agree that the risk of someone not understanding "division"
ways is much less than the risk of someone not understanding
"and" ways.
On 2025-08-19, Dan Cross <cross@spitfire.i.gajendra.net> wrote:
In article <1081rg2$3njqo$3@dont-email.me>,
Simon Clubley <clubley@remove_me.eisner.decus.org-Earth.UFP> wrote:
I write simple to understand code, not clever code, even when the
problem it is solving is complex or has a lot of functionality
built into the problem.
I've found it makes code more robust and easier for others to read, >>>especially when they may not have the knowledge you have when you
wrote the original code.
I'm curious how this expresses itself with respect to e.g. the
short-circuiting thing, though. For instance, this might be
common in C:
struct something *p;
...
if (p != NULL && p->ptr != NULL && something(*p->ptr)) {
// Do something here.
}
This, of course, relies on short-circuiting to avoid
dereferncing either `p` or `*p->ptr` if either is NULL. What
is the alternative?
if (p != NULL) {
if (p->ptr != NULL) {
if (something(*p->ptr)) {
// Do something....
}
}
}
If I dare say so, this is strictly worse because the code is now
much more heavily indented.
Indented properly (not as in your next example!) I find that very
readable and is mostly how I would write it although I do use code
like your return example when appropriate. This is my variant:
if (p != NULL)
{
if (p->ptr != NULL)
{
if (something(*p->ptr))
{
// Do something....
}
}
}
In case that doesn't survive a NNTP client, it is in Whitesmiths format:
https://en.wikipedia.org/wiki/Indentation_style#Whitesmiths
I like to spread out code vertically as I find it is easier to read.
We are no longer in the era of VT50/52/100 terminals. :-)
Ken Thompson used to avoid things like this by writing such code
as:
if (p != NULL)
if (p->ptr != NULL)
if (something(p->ptr)) {
// Do something....
}
YUCK * 1000!!! That's horrible!!! :-)
Which has a certain elegance to it, but automated code
formatters inevitably don't understand it (and at this point,
one really ought to be using an automated formatter whenever
possible).
AN alternative might be to extract the conditional and put it
into an auxiliary function, and use something similar to
Dijkstra's guarded commands:
void
maybe_do_something(struct something *p)
{
if (p == NULL)
return;
if (p->ptr == NULL)
return;
if (!something(*p->ptr))
return;
// Now do something.
}
I would argue that this is better than the previous example, and
possibly on par with or better than the original: if nothing
else, it gives a name to the operation. This is of course just
a contrived example, so the name here is meaningless, but one
hopes that in a real program a name with some semantic meaning
would be chosen.
There is one difference for me here however. _All_ single conditional >statements as in the above example are placed in braces to help avoid
the possibility of a later editing error.
readable and is mostly how I would write it although I do use code
like your return example when appropriate. This is my variant:
if (p != NULL)
{
if (p->ptr != NULL)
{
if (something(*p->ptr))
{
// Do something....
}
}
}
In case that doesn't survive a NNTP client, it is in Whitesmiths format:
On 20/08/2025 16:03, Dan Cross wrote:
In article <1082lks$3nmtt$2@dont-email.me>,
Chris Townley <news@cct-net.co.uk> wrote:
[snip]
Interestingly I have just come across an old bit of DEC Basic code:
REPORT.ONLY = W.S4 = "R" ! Global flag
I know what it does, but I would wrapped the knuckles of any programmer
who did that on my shift!
Not knowing DEC BASIC, am I correct in guessing that this
assigns the boolean result of comparing `W.S4` with the string
"R" to `REPORT.ONLY`?
Correct, but I would have surrounded the comparison with brackets, or
used an IF statement.
Not quite as bad as a colleague who found source code file for a
function, that ended with an UNLESS Z
Z was a global not mentioned in the source file! Try searching a massive >codebase for Z!
In article <1084fca$afbj$3@dont-email.me>,
Simon Clubley <clubley@remove_me.eisner.decus.org-Earth.UFP> wrote:
On 2025-08-19, Dan Cross <cross@spitfire.i.gajendra.net> wrote:
Even now, it's still an interesting read. I like my own code
princples, as well, but of course, I'm biased:
https://pub.gajendra.net/2016/03/code_principles
I've just read through that document and agree with everything there.
I was especially amused by the write for readability and it will be
read many times comments as I use that wording myself.
I am surprised you are picking me up on some things however, given
the mindset expressed in that document. Perhaps your idea of readability
is different from mine. :-)
Oh, I hope any criticism I offer doesn't come across as
personal!
On 20/08/2025 13:27, Simon Clubley wrote:
<big snip>> Indented properly (not as in your next example!) I find that >very
readable and is mostly how I would write it although I do use code
like your return example when appropriate. This is my variant:
if (p != NULL)
{
if (p->ptr != NULL)
{
if (something(*p->ptr))
{
// Do something....
}
}
}
In case that doesn't survive a NNTP client, it is in Whitesmiths format:
<snip>
That is why I don't like Whitesmiths
To me the curly braces should logically align with the preceding statement.
When I first looked at he example, I immediately thought there is a
missing closing brace, which of course there isn't.
I also dislike putting the opening brace at the end of the preceding
line, although I have had to in some cases. Probably a Microsoft invention
On 2025-08-20, Dan Cross <cross@spitfire.i.gajendra.net> wrote:
In article <1084fca$afbj$3@dont-email.me>,
Simon Clubley <clubley@remove_me.eisner.decus.org-Earth.UFP> wrote:
On 2025-08-19, Dan Cross <cross@spitfire.i.gajendra.net> wrote:
Even now, it's still an interesting read. I like my own code
princples, as well, but of course, I'm biased:
https://pub.gajendra.net/2016/03/code_principles
I've just read through that document and agree with everything there.
I was especially amused by the write for readability and it will be
read many times comments as I use that wording myself.
I am surprised you are picking me up on some things however, given
the mindset expressed in that document. Perhaps your idea of readability >>>is different from mine. :-)
Oh, I hope any criticism I offer doesn't come across as
personal!
No, it absolutely does _not_ in any way.
For me, it's exactly the same as a colleague noticing something
in another colleague's code or design proposal and commenting on it.
You would have to be extremely fragile to take _that_ personally. :-)
On 20/08/2025 16:03, Dan Cross wrote:
In article <1082lks$3nmtt$2@dont-email.me>,
Chris Townley <news@cct-net.co.uk> wrote:
On 19/08/2025 17:07, Dan Cross wrote:
In article <10822mn$3pb8v$1@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
On 8/18/2025 11:00 PM, Lawrence DrCOOliveiro wrote:
On Mon, 18 Aug 2025 21:49:29 -0400, Arne Vajh|+j wrote:
On 8/18/2025 7:59 PM, Lawrence DrCOOliveiro wrote:
On Mon, 18 Aug 2025 19:48:16 -0400, Arne Vajh|+j wrote:
On 8/18/2025 7:45 PM, Lawrence DrCOOliveiro wrote:
Parentheses are best used lightly -- where needed, maybe a little >>>>>>>>>> bit more than that, and thatrCOs it.
Otherwise parenthesis clutter introduces its own obstacles to >>>>>>>>>> readability.
That is not the mantra among people who try to prevent future >>>>>>>>> errors.
There are people who just repeat what they are told, arenrCOt there, >>>>>>>> instead of learning from actual experience.
It is the recommendation from people with actual experience.
One book that recommend it is "The Practice of Programming".
Brian Kernighan and Rob Pike.
One wonders how much experience they really have, across how many
different languages.
(Wow.)
Brian Kernighan and Rob Pike? A lot! :-)
It may help to read what they actually wrote in TPoP; on page 6:
|_Parenthesize to resolve ambiguity_. Parentheses specify
|grouping and can be used to make the intent clear even when
|they are not required. The inner parentheses in the previous
|example are not necessary, but they don't hurt, either.
|Seasoned programmers might omit them, because the relational
|operators (< <= == != >= >) have higher precedence than the
|logical operators (&& and ||).
|
|When mixing unrelated operators, though, it's a good idea to
|parenthesize. C and its friends present pernicious precedence
|problems, and it's easy to make a mistake.
For reference, the "previous example" they mention here is:
if ((block_id >= actblks) || (block_id < unblocks))
Most C programmers would write this as,
if (block_id >= actblks || block_id < unblocks)
And Kernighan and Pike would be fine with that. It must be
noted that, throughout the rest of TPoP, they rarely
parenthesize as aggressively as they do in that one example.
For example, on page 98, in the discussion of building a CSV
file parser interface, they present a function called,
`advquoted` that contains this line of code:
if (pj] == '"' && p[++j] != '"') {
...
}
(Note this doesn't just omit parenthesis, but also makes use of
the pre-increment operator _and_ boolean short-circuiting.)
Pike is famous for brevity; his 1989 document, "Notes on
Programming in C" is a model here:
http://www.literateprogramming.com/pikestyle.pdf
Even now, it's still an interesting read. I like my own code
princples, as well, but of course, I'm biased:
https://pub.gajendra.net/2016/03/code_principles
- Dan C.
Interestingly I have just come across an old bit of DEC Basic code:
REPORT.ONLY = W.S4 = "R" ! Global flag
I know what it does, but I would wrapped the knuckles of any programmer
who did that on my shift!
Not knowing DEC BASIC, am I correct in guessing that this
assigns the boolean result of comparing `W.S4` with the string
"R" to `REPORT.ONLY`?
- Dan C.
Correct, but I would have surrounded the comparison with brackets, or used an IF
statement.
Not quite as bad as a colleague who found source code file for a function, that
ended with an UNLESS Z
Z was a global not mentioned in the source file! Try searching a massive codebase for Z!
On 8/20/2025 11:51 AM, Dan Cross wrote:
In article <1084drl$afbj$1@dont-email.me>,
Simon Clubley <clubley@remove_me.eisner.decus.org-Earth.UFP> wrote:
On 2025-08-19, Dan Cross <cross@spitfire.i.gajendra.net> wrote:
In article <68a493ec$0$710$14726298@news.sunsite.dk>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
Kotlin is rather picky about mixing signed and unsigned.
var v: UInt = 16u
v = v / 2
gives an error.
v = v / 2u
v = v / 2.toUInt()
works.
I consider that rather picky.
I've not used Kotlin, but I consider that to be the really good type
of picky. :-)
It's kind of annoying that it can't infer to use unsigned for
the '2' in the first example. Rust, for example, does do that
inference which makes most arithmetic very natural.
I actually consider that to be a good thing. The programmer is forced
to think about what they have written and to change it to make those
intentions explicit in the code. I like this.
I think the point is, that in cases like this, the compiler
enforces the explicit typing anyway: if the program compiles, it
is well-typed. If it does not, then it is not. In that
context, this level of explicitness adds little, if any,
additional value.
That the literal "2" is a different type than "2u" is
interesting, however, and goes back to what you were saying
earlier about default signedness. As a mathematical object,
"2" is just a positive integer, but programming languages are
not _really_ a mathematical notation, so the need to be explicit
here makes sense from that perspective, I guess.
In Rust, I might write this sequence as:
let mut v = 16u32;
v = v / 2;
And the type inference mechanism would deduce that 2 should be
treated as a `u32`. But I could just as easily write,
let mut v = 16u32;
v = v / 2u32;
Which explicitly calls out that 2 as a `u32`.
Is this really better, though? This is where I'd argue that
matters of idiom come into play: this is not idiomatic usage in
the language, and so it is probably not better, and maybe worse.
The practical difference for specific code is likely zero.
But there is a difference in language principles and the
confidence the developer can have in it.
A rule that there is never any implicit conversion or
literal inference no matter the context is simple to
understand and gives confidence.
Exceptions even in cases where it does not matter adds
the complexity of understanding when the exceptions apply
and why they do not matter. Complexity that developers
would rather avoid.
On 8/19/2025 1:26 PM, Dan Cross wrote:
In article <10823ei$3pb8v$3@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
On 8/19/2025 9:01 AM, Simon Clubley wrote:
On 2025-08-18, Dan Cross <cross@spitfire.i.gajendra.net> wrote:
I happen to disagree with Simon's notion of what makes for
robust programming, but to go to such an extreme as to suggest
that writing code as if logical operators don't short-circuit
is the same as not knowing the semantics of division is
specious.
That last one is an interesting example. I may not care about
short circuiting, but I am _very_ _very_ aware of the combined
unsigned integers and signed integers issues in C expressions. :-(
It also affects how I look at the same issues in other languages.
I've mentioned this before, but I think languages should give you
unsigned integers by default, and you should have to ask for
a signed integer if you really want one.
"by default" sort of imply signedness being an attribute of
same type.
Why not just make it two different types with different names?
Whether we follow tradition and call them integer and cardinal
or more modern style and call them int and uint is less important.
I would argue that, at this point, there's little need for a
generic "int" type anymore, and that types representing integers
as understood by the machine should explicitly include both
signedness and width. An exception may be something like,
`size_t`, which is platform-dependent, but when transferred
externally should be given an explicit size. A lot of the
guesswork and folklore that goes into understanding the
semantics of those things just disappears when you're explicit.
The integer types should have well defined width.
And they could also be called int32 and uint32.
That seems to be in fashion in low level languages
competing with C.
Many higher level languages just define that int is 32 bit,
but don't show it in the name.
On 8/19/2025 1:26 PM, Dan Cross wrote:
And despite the old admonition to make everything a symbolic
constant, things like `2 * pi * r` are perfectly readable, and
I'd argue that `TWO * pi * r` are less so.
I would say that TWO and 2 are the same regarding readability.
The problem with TWO is not readability, but lack of purpose.
There are two good reasons to introduce symbolic names for constants:
1) The name can be more self documenting than a numeric value
2) If the constant is used multiple places, then having a symbolic
name makes it easier to change the value
But neither applies.
TWO does not provide more information than 2.
And it would be very unwise to change the value of TWO
to something different from 2.
In article <108dlq4$2fi6h$4@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
On 8/19/2025 1:26 PM, Dan Cross wrote:
In article <10823ei$3pb8v$3@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
Whether we follow tradition and call them integer and cardinal
or more modern style and call them int and uint is less important.
I would argue that, at this point, there's little need for a
generic "int" type anymore, and that types representing integers
as understood by the machine should explicitly include both
signedness and width. An exception may be something like,
`size_t`, which is platform-dependent, but when transferred
externally should be given an explicit size. A lot of the
guesswork and folklore that goes into understanding the
semantics of those things just disappears when you're explicit.
The integer types should have well defined width.
And they could also be called int32 and uint32.
That seems to be in fashion in low level languages
competing with C.
Many higher level languages just define that int is 32 bit,
but don't show it in the name.
If by "many higher level languages" you mean languages in the
JVM and CLR ecosystem, then sure, I guess so. But it's not
universal, and I don't see how it's an improvement.
(... somehow they fucked up longint and made it 32 bit on 32 bit and
64 bit Windows but 64 bit on 64 bit *nix)
On Sun, 24 Aug 2025 19:52:52 -0400, Arne Vajh|+j wrote:
(... somehow they fucked up longint and made it 32 bit on 32 bit and
64 bit Windows but 64 bit on 64 bit *nix)
It was *Microsoft* that rCLfucked up longintrCY, and nobody else. Just to be clear.
On Sun, 24 Aug 2025 19:52:52 -0400, Arne Vajh|+j wrote:
(... somehow they fucked up longint and made it 32 bit on 32 bit and
64 bit Windows but 64 bit on 64 bit *nix)
It was *Microsoft* that rCLfucked up longintrCY, and nobody else. Just to be clear.
But note that DEC made half step first: Alpha is 64-bit machine and
DEC made long 32-bit on Alpha.
On Mon, 25 Aug 2025 02:05:37 -0000 (UTC), Waldek Hebisch wrote:
But note that DEC made half step first: Alpha is 64-bit machine and
DEC made long 32-bit on Alpha.
On DEC Unix, as on every other *nix, rCLintrCY was 32 bits and rCLlongrCY was 64
bits. This applied on Alpha, too.
On 8/24/2025 7:27 PM, Dan Cross wrote:
In article <108dlq4$2fi6h$4@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
On 8/19/2025 1:26 PM, Dan Cross wrote:
In article <10823ei$3pb8v$3@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
Whether we follow tradition and call them integer and cardinal
or more modern style and call them int and uint is less important.
I would argue that, at this point, there's little need for a
generic "int" type anymore, and that types representing integers
as understood by the machine should explicitly include both
signedness and width. An exception may be something like,
`size_t`, which is platform-dependent, but when transferred
externally should be given an explicit size. A lot of the
guesswork and folklore that goes into understanding the
semantics of those things just disappears when you're explicit.
The integer types should have well defined width.
And they could also be called int32 and uint32.
That seems to be in fashion in low level languages
competing with C.
Many higher level languages just define that int is 32 bit,
but don't show it in the name.
If by "many higher level languages" you mean languages in the
JVM and CLR ecosystem, then sure, I guess so. But it's not
universal, and I don't see how it's an improvement.
That are two huge group of languages with a pretty big
market share in business applications.
Delphi provide both flavors. shortint/smallint/integer
and int8/int16/int32, byte/word/cardinal and
uint8/uint16/uint32. I believe the first are the most
widely used.
(64 bit is just int64 and uint64, because somehow they
fucked up longint and made it 32 bit on 32 bit and 64 bit
Windows but 64 bit on 64 bit *nix)
In article <108g8kk$33isk$1@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
On 8/24/2025 7:27 PM, Dan Cross wrote:
In article <108dlq4$2fi6h$4@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
On 8/19/2025 1:26 PM, Dan Cross wrote:
In article <10823ei$3pb8v$3@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
Whether we follow tradition and call them integer and cardinal
or more modern style and call them int and uint is less important.
I would argue that, at this point, there's little need for a
generic "int" type anymore, and that types representing integers
as understood by the machine should explicitly include both
signedness and width. An exception may be something like,
`size_t`, which is platform-dependent, but when transferred
externally should be given an explicit size. A lot of the
guesswork and folklore that goes into understanding the
semantics of those things just disappears when you're explicit.
The integer types should have well defined width.
And they could also be called int32 and uint32.
That seems to be in fashion in low level languages
competing with C.
Many higher level languages just define that int is 32 bit,
but don't show it in the name.
If by "many higher level languages" you mean languages in the
JVM and CLR ecosystem, then sure, I guess so. But it's not
universal, and I don't see how it's an improvement.
That are two huge group of languages with a pretty big
market share in business applications.
Market share is not the same as influence, and while the JVM/CLR
languages _do_ have a lot of users, that does not imply that all
are good languages. In fact, only a handful of languages in
each family have any significant adoption, and I don't think PL
designers are mining them for much inspiration these days.
Again, not universal, nor really an improvement over just using
explicitly sized types.
Delphi provide both flavors. shortint/smallint/integer
and int8/int16/int32, byte/word/cardinal and
uint8/uint16/uint32. I believe the first are the most
widely used.
The older names feel like they're very much looking backwards in
time.
(64 bit is just int64 and uint64, because somehow they
fucked up longint and made it 32 bit on 32 bit and 64 bit
Windows but 64 bit on 64 bit *nix)
I'd blame C for that.
On 8/29/2025 9:17 AM, Dan Cross wrote:
In article <108g8kk$33isk$1@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
On 8/24/2025 7:27 PM, Dan Cross wrote:
In article <108dlq4$2fi6h$4@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
On 8/19/2025 1:26 PM, Dan Cross wrote:
In article <10823ei$3pb8v$3@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
Whether we follow tradition and call them integer and cardinalI would argue that, at this point, there's little need for a
or more modern style and call them int and uint is less important. >>>>>>
generic "int" type anymore, and that types representing integers
as understood by the machine should explicitly include both
signedness and width. An exception may be something like,
`size_t`, which is platform-dependent, but when transferred
externally should be given an explicit size. A lot of the
guesswork and folklore that goes into understanding the
semantics of those things just disappears when you're explicit.
The integer types should have well defined width.
And they could also be called int32 and uint32.
That seems to be in fashion in low level languages
competing with C.
Many higher level languages just define that int is 32 bit,
but don't show it in the name.
If by "many higher level languages" you mean languages in the
JVM and CLR ecosystem, then sure, I guess so. But it's not
universal, and I don't see how it's an improvement.
That are two huge group of languages with a pretty big
market share in business applications.
Market share is not the same as influence, and while the JVM/CLR
languages _do_ have a lot of users, that does not imply that all
are good languages. In fact, only a handful of languages in
each family have any significant adoption, and I don't think PL
designers are mining them for much inspiration these days.
Again, not universal, nor really an improvement over just using
explicitly sized types.
It is a huge domain that are totally dominated by two approaches:
[snip]
Delphi provide both flavors. shortint/smallint/integer
and int8/int16/int32, byte/word/cardinal and
uint8/uint16/uint32. I believe the first are the most
widely used.
The older names feel like they're very much looking backwards in
time.
Developers tend to like what they know.
(64 bit is just int64 and uint64, because somehow they
fucked up longint and made it 32 bit on 32 bit and 64 bit
Windows but 64 bit on 64 bit *nix)
I'd blame C for that.
Delphi is not C.
In article <108t0d4$249vm$11@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
On 8/29/2025 9:17 AM, Dan Cross wrote:
In article <108g8kk$33isk$1@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
Delphi provide both flavors. shortint/smallint/integer
and int8/int16/int32, byte/word/cardinal and
uint8/uint16/uint32. I believe the first are the most
widely used.
The older names feel like they're very much looking backwards in
time.
Developers tend to like what they know.
(64 bit is just int64 and uint64, because somehow they
fucked up longint and made it 32 bit on 32 bit and 64 bit
Windows but 64 bit on 64 bit *nix)
I'd blame C for that.
Delphi is not C.
Obviously.
But it would be foolish to assume that they weren't influenced
by matters of compatibility with C (or more specifically C++)
here, particularly given the history of Delphi as a language.
Even the name gives it away ("longint").
In article <108t0d4$249vm$11@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
On 8/29/2025 9:17 AM, Dan Cross wrote:
In article <108g8kk$33isk$1@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
On 8/24/2025 7:27 PM, Dan Cross wrote:
In article <108dlq4$2fi6h$4@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
On 8/19/2025 1:26 PM, Dan Cross wrote:
In article <10823ei$3pb8v$3@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
Whether we follow tradition and call them integer and cardinal >>>>>>>> or more modern style and call them int and uint is less important. >>>>>>>I would argue that, at this point, there's little need for a
generic "int" type anymore, and that types representing integers >>>>>>> as understood by the machine should explicitly include both
signedness and width. An exception may be something like,
`size_t`, which is platform-dependent, but when transferred
externally should be given an explicit size. A lot of the
guesswork and folklore that goes into understanding the
semantics of those things just disappears when you're explicit.
The integer types should have well defined width.
And they could also be called int32 and uint32.
That seems to be in fashion in low level languages
competing with C.
Many higher level languages just define that int is 32 bit,
but don't show it in the name.
If by "many higher level languages" you mean languages in the
JVM and CLR ecosystem, then sure, I guess so. But it's not
universal, and I don't see how it's an improvement.
That are two huge group of languages with a pretty big
market share in business applications.
Market share is not the same as influence, and while the JVM/CLR
languages _do_ have a lot of users, that does not imply that all
are good languages. In fact, only a handful of languages in
each family have any significant adoption, and I don't think PL
designers are mining them for much inspiration these days.
Again, not universal, nor really an improvement over just using
explicitly sized types.
It is a huge domain that are totally dominated by two approaches:
[snip]
So? You referred to "many higher level languages". That is
qualitatively different than "a small number of languages with a
huge share of the market."
On 8/29/2025 5:38 PM, Dan Cross wrote:
In article <108t0d4$249vm$11@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
On 8/29/2025 9:17 AM, Dan Cross wrote:
In article <108g8kk$33isk$1@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
Delphi provide both flavors. shortint/smallint/integer
and int8/int16/int32, byte/word/cardinal and
uint8/uint16/uint32. I believe the first are the most
widely used.
The older names feel like they're very much looking backwards in
time.
Developers tend to like what they know.
(64 bit is just int64 and uint64, because somehow they
fucked up longint and made it 32 bit on 32 bit and 64 bit
Windows but 64 bit on 64 bit *nix)
I'd blame C for that.
Delphi is not C.
Obviously.
But it would be foolish to assume that they weren't influenced
by matters of compatibility with C (or more specifically C++)
here, particularly given the history of Delphi as a language.
Even the name gives it away ("longint").
That was also Lawrence's guess.
But the hypothesis that they wanted to follow
C/C++ is obviously not true.
On 8/29/2025 5:38 PM, Dan Cross wrote:
In article <108t0d4$249vm$11@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
On 8/29/2025 9:17 AM, Dan Cross wrote:
In article <108g8kk$33isk$1@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
On 8/24/2025 7:27 PM, Dan Cross wrote:
In article <108dlq4$2fi6h$4@dont-email.me>,
Arne Vajh|+j <arne@vajhoej.dk> wrote:
On 8/19/2025 1:26 PM, Dan Cross wrote:
In article <10823ei$3pb8v$3@dont-email.me>,The integer types should have well defined width.
Arne Vajh|+j <arne@vajhoej.dk> wrote:
Whether we follow tradition and call them integer and cardinal >>>>>>>>> or more modern style and call them int and uint is less important. >>>>>>>>I would argue that, at this point, there's little need for a
generic "int" type anymore, and that types representing integers >>>>>>>> as understood by the machine should explicitly include both
signedness and width. An exception may be something like,
`size_t`, which is platform-dependent, but when transferred
externally should be given an explicit size. A lot of the
guesswork and folklore that goes into understanding the
semantics of those things just disappears when you're explicit. >>>>>>>
And they could also be called int32 and uint32.
That seems to be in fashion in low level languages
competing with C.
Many higher level languages just define that int is 32 bit,
but don't show it in the name.
If by "many higher level languages" you mean languages in the
JVM and CLR ecosystem, then sure, I guess so. But it's not
universal, and I don't see how it's an improvement.
That are two huge group of languages with a pretty big
market share in business applications.
Market share is not the same as influence, and while the JVM/CLR
languages _do_ have a lot of users, that does not imply that all
are good languages. In fact, only a handful of languages in
each family have any significant adoption, and I don't think PL
designers are mining them for much inspiration these days.
Again, not universal, nor really an improvement over just using
explicitly sized types.
It is a huge domain that are totally dominated by two approaches:
[snip]
So? You referred to "many higher level languages". That is
qualitatively different than "a small number of languages with a
huge share of the market."
Yes - that is two different statements.
But they are both true.
And the second qualifies the first in the sense that the
many are actually some that matter not pure exotic.