If you didn't have to care about backwards compatibility, what would you change about it?

...

Other urls found in this thread:

doc.rust-lang.org/std/ops/trait.Deref.html#more-on-deref-coercion
twitter.com/SFWRedditImages

no header files and properly implemented packages/libraries/modules/namespaces or whatever people like to call it

Plan 9 C is pretty much perfect. There's Go on Plan 9, and nobody ever uses it, before it doesn't offer an advantage over Plan 9 C like it does over *nix C.

utf-8 strings in std library
hash maps in standard library
templates over void*+size_t duo, slower compilation and slightly more complex preprocessor/linker, but cleaner interfaces and faster code
not sure if some cleaner way of scoping resources is necessary (defer, RAII+destructors)

s/before/because

This.

The problem with C is its retarded standard library, which is too error-prone. Some software, like qmail, even ignore it altogether and work around it.

Add a # to the name.

Nothing, fuck off ya cunts and learn to program

Unnamed substructs was a comfy extension (similar to embedding in Go and Rust).

Better pointer syntax to end the confusion about when and where to put a * when using pointers.

It's really not that fucking hard, and I'm willing to bet more people would use C if that syntax was cleaner.

>more people using C
Why would you want that?

kek'd

>no header files and properly implemented packages/libraries/modules/namespaces or whatever people like to call it
why?
what's wrong with headers?

>This.
>The problem with C is its retarded standard library, which is too error-prone. Some software, like qmail, even ignore it altogether and work around it.
LOL!!!!!!!!
the standard library is implementation defined. it's only as good as how you program your own standard library.

>Better pointer syntax to end the confusion about when and where to put a * when using pointers.
>It's really not that fucking hard, and I'm willing to bet more people would use C if that syntax was cleaner.
is this really the only complaint people have about C?

they exist in C11 desu

Namespace pollution and not having shit defined in exactly one place.

The standard library has worse problems than specific implementations.

add strings?

Wow, didn't notice that before, thanks. Good reason to stop typing -std=c99 everywhere.

A standard pointer syntax (int*, not int *).
Some kind of templating system (all the options for implementing a map currently suck).
Namespaces.
C++ style struct definitions that don't require that typedef make-work.
A defer keyword for closure-like behavior.
A fallthrough keyword and an end to implicit fallthrough for non-empty cases.
Standard library strings and containers.

Disgusting

Oh and doing away with type names with spaces in them. There is no reason for "unsigned long long" to be a valid construct.

remove the randomness when i put one = in the if/do/while/for and just treat it as ==
also fix the way it takes care of stacks. stack buffer overflow is a pain

the standard library is only declared, it's not defined. you have to implement it.
still, headers with an #include are defined exactly in place after the preprocessor runs. what's the problem?

...

>the standard library is only declared, it's not defined. you have to implement it.
It's declared so badly implementing it should be a crime, as most actual crimes have resulted in less damage.

there is absolutely no need for the program to assign value while checking the condition

Function pointers are an abomination.

...

upvoted

unless assignment returns an assigned value
in C it's valid and reasonable construct because `if` implicitly checks for bitwise 0 value and not logical true

the "if" is there to check the condition, not to assign a value. if it assigns the value then it doesn't check the condition at all

How do you pass callback functions to other functions then?

declaration syntax, something like go

Use an interface, duh.

by string with function name

How are interfaces implemented?

Wow! Maybe it works in abstracted mind, but not on this machine architecture.

>something something first-class functions

>passing first-class functions
I wonder how it all comes down in assembler...
>function at address X
>load X
>call X
At heart, it's still an indirect call to procedure, precisely what a function pointer is good for, anything else is boilerplate out of the current model of computation.

Add generic types (no templates).
Add a proper module system, not .h and .c.
No preprocessing.
No implicit cast.
Statically typed malloc.
A true const semantics.

Use sensible declaration syntax.
Tuples. A standard library that returns (val, err) tuples instead of doing any of that out parameter or errno bullshit.
Arrays don't implicitly decay to pointers, just to strengthen the consistency of value semantics.

Anything more than that and I'd be designing a C++ replacement instead.

That's not what first class functions are.

What's the punchline? That the author doesn't know how to configure his own environment and use the correct character encoding?

>A defer keyword for closure-like behavior.
Can you explain what you mean by closure like behavior here?

The syntax is. The concept is not.

It's pretty common in C to check for a return type as a file is opened within the same line of code

Make & and * postfix operators.

What would they do?

The same thing they do now, it just means fewer parentheses and a more obvious order of operations.

that's completely different. not even brainlets write such code

But now we'd have two languages called C#, why would you want that?

Remove all pointer typer except void.

No pointers

Why do you even need to keep void* then? Just use intptr_t. You're going to need explicitly typed peek/poke operations anyway.

Back to BCPL and Hungarian notation

>not escaping your expressions

* referencing
& derreferencing

Example:
&a = address of a
*a = actually accesing the thing a is pointing at.

fuck yeah

How would you implement RAII in C?

>struct embedding in rust
doesn't exist

sounds like rust with no safety checks and C syntax

Probably the underscore stuff. I mean you can always just use macros and includes for bools, uint64_t and other relatively standard stuff, so it's mostly syntax.

Featurewise, compile time computation would be great, so we don't have to use magic numbers or make a weird makefile that #include's the output of a different program. Also, having something for unicode.

Aside from those, it's perfect.

No malloc and free. Would make alloca an intrinsic that allocates on the heap but is automatically freed on return from the function (RAII style)

Congratulations, you've just made the heap completely useless.

>create proper, modular, tiered stdlib
>remove headers, introduce proper modules and import system where the importer can define a package name
>no longer a one pass compiler
>remove object files, linker, create better ABI
>remove preprocessor entirely
>introduce full compile time execution and AST introspection which also removes the need for shitty build systems
>introduce go-to metaprogramming like simple templates and operator overloading
>add traits for dynamic dispatch
>add multiple returns
>add proper type system with a it's-just-bytes-man declaration keyword
>add proper enums
>clean up syntax, in particular most forms of declaration syntax
>optionally: change syntax to word-based since it's objectively the best, according to the Quorum scientist

You're no longer making a better C, you're making a better C++.
>add multiple returns
dumb shit, use tuples.

>tuples
dumb shit, use multiple return values and anonymous structs
>You're no longer making a better C, you're making a better C++.
Also called "C if it wasn't made by tards and if it werent incomplete".
There is no place for a watered-down brainlet language. There is no place for brainlets in programming.

hope you're not actually serious

Multiple return values are just a shitty limited version of tuples. Limiting the user like that would be like making printf an intrinsic and lacking any support for user defined variadic argument lists.
>anonymous structs
How would destructuring work?
>C if it wasn't made by tards and if it werent incomplete
C is complete, slimy sepplesfag. Completeness is not achieved by adding dozens of orthogonal and incompatible methods of achieving the same thing, only unnecessary complexity.

>Multiple return values are just a shitty limited version of tuples.
No. Multiple return values are automatically structured and destructured and could be used together with anonymous structs, which is probably what you have in mind, when you said "tuples", aka C# "tuples". Actual tuples are accessed by index and to support that in statically typed languages you need some shitty metaprogramming hacks that are not nice, because an index operation implies runtime values, whereas macro/value-template limit it to literals/values that can be computed at compile time.
Basically, strict tuples have a fucked up interface.
>How would destructuring work?
By name or by order, like normal destructuring.
>C is complete, slimy sepplesfag.
>muh unnecessary complexity
>t. brainlet Cnile.
I agree that C++ is garbage and that many features fight each other.
That said, programming languages that require a build system and can't express all set operations/relations for type declarations are incomplete.

>muh C is complete
Why are you even in this thread, user. You have nothing to win and everything to lose here...

Because C isn't perfect. C might have flaws but that doesn't mean its overall philosophy is mistaken.

It's literally in the linux kernel

Why would tuples need to be indexed by runtime values?
Conceptually a tuple is just a struct with enumerated instead of named members. If struct "indexers" are constant expressions, that's all tuple indexers need to be.
If this is a first class language feature rather than a post hoc template hack, you can get a simple and clean interface analogous to that for structs. Here's an example from Rust.
let tup : (i32, char) = (10, 'h');
let x : i32 = tup.0; // constant expression indexer
let y : char = tup.1;
let (a, b) : (i32, char) = tup; // easy destructuring
Now that I'm writing this out, it seems like collapsing anonymous structs and tuples into the same feature could be suitably elegant.
How would what you're suggesting look syntactically?

>Why would tuples need to be indexed by runtime values?
I don't really like operators overloaded on built-in language features.

>Rust example
I don't know Rust. Is this an actual index operator or is this dereferenced names allowing digits as names or is that the dereference operator being overloaded?

>How would what you're suggesting look syntactically?
Always enforce using member names, except for maybe ordered destructuring.
It's annoying to write, but it is a hell more self-documenting and error messages will be better. Stuff like this is why I get nightmares about error messages like:
Type mismatch:
tuple(list[tuple(int,int)], list[tuple(int, bool)])
vs
tuple(list[tuple(int,int)], list[tuple(float, bool)])

only more nested.

Algebraic types,null checkers,pattern match,nuked switch, = to := and == to =, logic operators(&&,||) to keywords and,or,xor,not

Dot is still a member access operator, same as for a struct. It's not indexing like an array, it's resolved at compile time.
Practically it's as if you have members named 0, 1, 2 instead of foo, bar, baz.
>Always enforce using member names, except for maybe ordered destructuring.
I'd just like to see a short example of how you'd envision an anonymous struct with multiple values being returned from a function and then extracting those values.

What is word-based syntax?

pointer instead of T* and the likes I guess

>How would you implement RAII in C?
That would be very hard with what C has to offer. Defer keyword as in Go that puts call on function-scoped stack and executes them when function exits wouldn't work well without closures. Smart pointers with destructor would require too much OOP from C++ and probably generics. Not sure how to implement it and keeps specs small at the same time.

>struct embedding in rust doesn't exist
it has Deref mechanism, result is very similar
doc.rust-lang.org/std/ops/trait.Deref.html#more-on-deref-coercion

How so?

Why do you ask? Is there a reason this would be bad?

The entire point of the heap is for allocations which outlive the current scope. Anything else can be an automatic (stack) variable.

__attribute__((__cleanup__(dtor)))

you're dumb
int a = 1;
if (a ^= 1) {
// Not executed
} else if (a = 0) {
// Also not executed
} else if (a = 1) {
// Executed
puts("nigger");
}

are you stupid? this is pretty much what any programmer worth does
if ((p = fork() == 0) {
//whatever
}

fuck i missed a bracket after fork(), oh well

They could still outlive the current scope if they were alloc'ed in the uppermost fuction that needed them.

realloc would still be usable in this setup but the return values from alloca and realloc would need to be win32 api style handles rather than just regular pointers.

>They could still outlive the current scope if they were alloc'ed in the uppermost fuction that needed them.
Then you declare an automatic variable in that function. Passing pointers to buffers allocated higher in the call stack happens all the time in C.

Nothing. It's a pleb filter.

>t. visual studio babby

>memcpy(x&, y& + offset, size)
looks great!

Doesn't look that bad next to (*f)() or (*a)[n]. Plus it means you can get rid of the -> operator and resolve the silly int* foo; int *foo; controversy for good.

ok, sorry that was too easy
x * y
is x a number type or a pointer?

A number type because * is only defined as a binary operator for numbers. Are you retarded?

LOL theres no ducktyping here, you "retard". that might aswell have been a programmer mistake, but you wouldnt know would you? postfix unary operators dont work if the binary ones are infix

> postfix unary operators dont work if the binary ones are infix
That's blatantly false and completely unfounded. Have you never written Pascal?

Just call it C##, duh.

the same symbol having different meanings with the same surroundings but different context is just bad. and i now realize that theres `y * *x` in C, and that theres no prob with it...
>Have you never written Pascal?
no i dont know anything about pascal other than that it allows defining functions inside functions (yay) and its older than C. fill me in

The deference operator in Pascal is ^ instead of * and it's postfix instead of prefix. y^ ^ x is unambiguous for the same reason that x * *y is unambiguous.

take current Rust and rename it to C.
done

ok, i concede, having the (de)reference operator postfix is not a problem, but then, why postfix instead of prefix? its essentially the same

The main motivation is simplified order of evaluation and fewer parens.
The behavior *p[n] isn't obvious until you learn the order of evaluation. p[n]* is clearer to novices. At the same time, (*p)[n] is messier than p*[n] despite both behaving in an obvious way.
Besides that you can also remove unnecessary operators like -> (simply becomes *.). You'd be surprised how many C noobies get confused about what -> does.
The declaration syntax becomes simpler too.

It's a small change but I think it would make for an overall nicer experience.