Is there a language that encourages good coding practices?
While I love PHP I find its biggest weakness is that it allows and even almost encourages programmers to write bad code.
Is there a language that encourages good programming practices? Or, more specifically, a web-related language that encourages good practices.
I'm i开发者_StackOverflow中文版nterested in languages who have either a stated goal of encouraging good programming or are designed in such a way as to encourage good programming.
I think Python have some ideas for good coding practices. At least programs are forced to look the same way.
But don't forget that Larry Wall said:
Real programmers can write assembly code in any language
You'd better think about creating a coding style convention.
This is way too subjective. If by "good programming practices," you mean consistent indentation, then sure, Python works for that. But indentation is something most programmers learn the first time they write a program. I think good programming goes well beyond that.
Over the years, the idea of what is good programming practice has changed. Python, other than the indentation thing, doesn't really excel in any one category. It's not the most object-oriented language around, nor does it (yet) offer full support for functional programming.
Here are some possible definitions of good programming practices, and a representative language for each:
- Pure object oriented design: SmallTalk was the first real OO language, and in some ways still the purest. Literally everything is a class.
- Pragmatic object oriented design: Java, for all it's detractors, was a huge step forward in terms of encouraging good programming practices. It is strongly typed, almost everything is a class, and it requires self-documenting class design, to a certain extent (by explicitly listing thrown exceptions, making functions private by default, etc.) Java enforces disciplines that are valuable for large development teams.
- Functional programming Haskell is often praised as being the most purely functional language around. Assignment is verboten, and side effects are impossible unless your function explicitly asks for them.
- Robust concurrency Erlang (another language that encourages the functional programming paradigm) is known for its robustness in a concurrent environment. Never having studied or used it, I can't personally vouch for this, but its track-record seems impressive.
- Iterative development There are a ton of Lisp evangelists out there. They can't all be wrong, can they?
- Quick 'n' dirty Sometimes you just need a script done quickly. Thank you, Perl. ;)
Well, it depends on what you consider a web language. Smalltalk definitely encourages best practices, and there's even a crazy web framework written in it (Seaside). It's very different and you can still do bad things. You're simply encouraged to do otherwise.
Eiffel's big thing is Design By Contract. It's a nifty organizational requirement that encourages testing and assertions everywhere.
Python is great, but it doesn't really encourage good practices. Well, if indentation is a best practice, then Python definitely enforces it.
Other languages don't really encourage you to do bad things like PHP does. You can also write great (and proper) code in PHP. People often forget that you can disable much of the nastiness in the interpreter (globals, slashes, etc.). You needn't jump ship just because PHP merely entices you to the dark side.
There is No Silver Bullet. Technology will not make a better programmer of you.
PASCAL is one of the programming languages that encourages good programming practices
Short answer? No. But the question uses English-language ideas that don't lend themselves to computer programming. What does "encourage" mean? What is "good programming practice"? Syntax highlighting and auto-indent? Surely any language can do that. Lint-style warnings? Not terribly hard. Style policing? Well, we'd had to admit C if that was the criteria.
Good programming practice arises naturally from good design. It's quite hard for clever coders to write bad code in any language if the design is clean and simple. Conversely bad practice follows from bad design. The tricky part is working out where a design stops being good and starts being bad. This is the #1 question in software design and sadly there is no silver bullet. Those lovely Design Patterns start looking awfully ugly once you have several of them implemented in your app.
This is pretty subjective, but I would have to say Python. Readability counts and there is only one way to do things make the language very easy to work with.
Frameworks can also reinforce good practices. Python's Django framework is based off the "MTV" pattern and lends itself to very friendly code.
I think really what you're looking for is not a programming language that encourages best practices, but an opinionated web development framework.
Ruby on Rails for instance is very opinionated, and "out of the box" gives you a strong indication of how the framework expects you to interact with it - it automatically creates a project structure, and even provides some initial unit tests. Testing is a very integral part of rails development, and you'll find a lot of resources to support BDD, TDD and other good "agile" development practices.
Other frameworks like Django (python) and Seaside (smalltalk) probably have their own conventions, although I'm not personally familiar with them.
I'm going to attract flames and suggest Perl.
'WTF?' you may say. Perl has a reputation as a write only language. It is, when in the hands of people who use it as merely a super-shell language. You can write crap in any language. Perl gives you massive freedom and flexibility. So, in Perl, logically, you have more freedom to write crappier crap.
The freedom and flexibility can also be used in the cause of readability and maintainability.
But how do you learn to produce good code and not crap? In the past the answer was "Experience, and community involvement." Over the last few years, some new tools and resources have arrived to help as well.
Experience
- If you write a turd, and have to maintain that turd, you will learn from the experience.
- Lovely. How do you avoid writing turds in the first place?
Community
- Instead of enforcing arbitrary rules in the language, Perl has cultural norms that help improve code.
- Post code on perlmonks without strict and warnings, and you will hear about why you should use them.
- Great, so to do a decent job, I need to spend hours reading websites and newsgroups? Well, you're here now. But this is still a sub-optimal solution.
Tools: This is where we hit paydirt -
- A few years ago, Perl Best Practices was published. It codified and collected the ideas of many leaders in the Perl community. It provides detailed discussion of the reasoning behind each of the 256 suggested practices. It offers practices, and a way of thinking about the practice of programming.
- perltidy is a great reformatter for Perl that promotes code readability by automatically enforcing formatting style.
- Perl::Critic and supporting modules provide a highly configurable system for analyzing Perl code. PC goes way beyond basic lint and even refers you to a specific page in Perl Best Practices for each issue it finds, allowing you to improve your code, five levels beyond the syntax check.
- Unit testing is a pervasive part of Perl culture. Perl offers great unit testing tools as part of the 5.10 distribution. Additional testing tools are available from CPAN.
- Moose is a new object system for Perl 5. It is inspired by the Perl 6 object system. Moose provides advanced object oriented capabilities like roles and traits. Roles and traits provide powerful new ways of handling code composition and reuse beyond what is possible with inheritance, interfaces and mix-ins. Inheritance models an "IS A" relationship. Roles and traits model "DOES". I can't emphasize enough how useful this is.
You can follow good practices in any language.
Yet you can carry out bad practices in any language as well.
As for writing "bad" code...you have to learn not to do that ;)
As for writing "well styled" code - grab a copy of Visual Studio, the ReSharper plugin, and StyleCop. Intellisense and autoformatting (Visual Studio) will help you lay things out nicely, the ReSharper plugin will restructure your code into a "preferred" structure, and StyleCop will help you follow a standard.
If I'm reading the question correctly, what you're looking for is a language where the "easy" thing to do and the "Best practices" thing to do are closely aligned.
If that's the case, what are the "best practices?" Gotta start with that :)
And as a slightly bizarre suggestion, might I suggest LISP or Scheme?
Haskell.
- It makes you write pure code separately
- It uses a tab syntax, forcing whitespace
- The module system allows effortless organization of code
Why are you asking? The question seems to come up a lot after I deal with some nasty code hairball. I spend hours picking apart spaghetti logic that trails through about 6 subroutine levels. Finally track down the niggling error. And my first thought is why can't this be easier?
Code is written for the computer - not humans. It's optimized for the machine. Machines require exact instructions. At that level of detail, the complexity of any code base goes up fast. And that complexity is what typically drives this question.
Programming languages are not intended to control complexity. Programming tools can help you do that. How you write your code matters a lot more than in what language you write your code.
Take a look at literate programming. It controls complexity through organization. I personally like the visual structure provided by the Leo editor.
You might want to read the seaside book to get some ideas on how to DRY web apps. The elimination of templates, consequent construction of DSLs for html and javascript frameworks (a.o. jQuery, Scriptaculous, Prototype, RaphaelJs) and even css (Phantasia, not in the base distribution), combination with an OODB for persistence (Gemstone) provides a lot of why is the current state of the art in php, java, ruby or c# so much worse?
I can't believe nobody has mentioned Objective-C / Cocoa. You are encouraged throughout to follow MVC patterns, and loose typing allows for some seriously decoupled OO designs.
Of course, this depends on what one thinks are "good practices". Different languages generally try to enforce/encourage their own opinions of what are "good coding practices".
Some examples of good practices that some languages try to encourage are:
Indenting code in logical levels:
If there's 1 practice that pretty much all programmers agree is good practice, it's that different blocks of code should be indented.
For example, consider the following Java code:
static boolean isPrime(final int x) {
if (x % 2 == 0 && x != 2) {
return false;
} else if (x > 1) {
final int MIDWAY = (x-1) / 2;
for (int i = MIDWAY; i > 1; i--) {
if (x % i == 0) {
return false;
}
}
return true;
}
return false;
}
It's considered best practice to indent the code within different scopes (e.g. function body, for
block, if
block). However, you don't HAVE to indent your code in a consistent manner (or even at all) in most languages. There's nothing stopping me from writing the whole thing without indentation, like this:
static boolean isPrime(final int x) {
if (x % 2 == 0 && x != 2) {
return false;
} else if (x > 1) {
final int MIDWAY = (x-1) / 2;
for (int i = MIDWAY; i > 1; i--) {
if (x % i == 0) {
return false;
}
}
return true;
}
return false;
}
You could even write the whole thing on 1 line if you wanted to! The code will still work, but it'll be a lot less readable.
However, languages that use offside-rule syntax (e.g. Python, Nim) FORCE you to indent your code in a consistent manner. So for example, the following Python code:
def is_prime(x):
if x % 2 == 0 and x != 2:
return False
elif x > 1:
MIDWAY = int((x-1) / 2)
for i in range(MIDWAY, 1, -1):
if x % i == 0:
return False
return True
return False
HAS to be indented. It won't run if it isn't. It can't. I can't write this code without indentation because blocks are determined BY indentation (and not {}
, which is what most languages use).
Ok, Python does allow you to be a LITTLE flexible with your indentation. 1-liners can go on the same line, like this:
def is_prime(x):
if x % 2 == 0 and x != 2: return False # This is allowed.
elif x > 1:
MIDWAY = int((x-1) / 2)
for i in range(MIDWAY, 1, -1):
if x % i == 0: return False # So is this
return True
return False
But that's only for 1-liners. Blocks that contain multiple statements (e.g. the elif
block) can't be done on 1 line.
Naming constants LIKE_THIS:
A common coding convention is to name constants CAPITALISED_WITH_UNDERSCORES. That's just so you (and other programmers) can distinguish, at a glance, a normal variable from a constant.
Now Ruby doesn't have user-defined constants (sob), but they have something like it: Ruby will give you a warning if you attempt to change a variable named LIKE_THIS. E.g.
my_var = 5 # creating a normal variable
my_var = 42 # this is ok
puts my_var
ANOTHER_VAR = 21 # creating a pseudo-constant
ANOTHER_VAR = 32 # interpreter will complain about this
puts ANOTHER_VAR # Will still work though
This output of this code is:
42
test.rb:5: warning: already initialized constant ANOTHER_VAR
test.rb:4: warning: previous definition of ANOTHER_VAR was here
32
In this way, Ruby encourages (but doesn't force) you to follow the best practice of naming your constants with UPPERCASE_WITH_UNDERSCORES.
Using constants over variables:
Typically, if you create a variable that you only assign to once (maybe it's just to hold an intermediate value, or you just don't need to re-assign to it), that variable should PROBABLY be a constant (e.g. the MIDWAY
var in the above Java code; if I don't intend to re-assign to it, why not make that intent explicit to others by making it constant?).
In Rust, variables are immutable (i.e. constant) by default, unless you specify otherwise (which is the opposite of what Java and C++ does). Example Rust code:
let x = 42; // declaring an immutable variable
x = 10; // compiler will give an error; can't reassign to x.
let mut y = 42; // declaring a mutable (i.e. "normal") variable
y = 10; // allowed
In this sense, Rust encourages you to use constants by default, and to really think about when they should be variables (whereas in most other languages you use variables by default and rarely think about when they should be constants).
NOTE: TECHNICALLY immutable variables aren't the same thing as constants in Rust (Rust actually has constants, declared with the const
keyword, but those are evaluated at compile-time). But since they act like constants in other languages, I'll call them constants for the purposes of this post.
Apart from those, most languages won't so much encourage you to actively use good practices as they will discourage (or just outright prevent) you from using "bad" practices.
For example, common wisdom says that using goto
is bad practice, so most languages don't even have goto
(the exceptions being C & C++)!
From here though, opinion tends to differ on what features are considered to be so bad (in terms of encouraging "bad practice") they're worth not having. For example, overuse of break
and continue
in loops is considered to be bad practice (for similar reasons to goto
), so Scala doesn't even have break
or continue
(well, at least not built in to the language)! The designers of Go thought that exception-handling tended to be abused (i.e. tempted programmers to write convoluted code and treat too many ordinary errors as "exceptional"), so Go doesn't even have exception-handling! Many languages consider code abusing the ++
and --
operators to be tricky and obscure, so they just don't outright have those operators (Rust, Python, Swift 4, etc). Note that there's not as much consensus here of what's considered good and bad practice.
So there you go, a by-no-means-exhaustive list (might add to it in the future) of some languages that try to encourage good coding practices in 1 way or another (or at least what they consider to be good coding practices).
I'd throw C# out there. It encourages good techniques, readable code and provides tools for ensuring your comments are useful and targetted.
They also provide static analysis tools out of the box to make sure the code is good.
to be clear You can write bad code in any language
anyway C# is really good for following good coding practices
C# undoubtedly... good base and constantly improving.
Yes, Python. Many of its design goals are for the stated purpose of encouraging good coding practices. Read the Python tutorial, and the Zen of Python (type "import this" at a Python prompt).
Coding practices are external to a language. You can just about muck up source code in any language and what is a good practice is subjective.
For example, in C# at the function level you can declare any variable using var and the compiler will enforce type safety, however many people don't like var and think it lends itself to making the code harder to decipher. I personally love var especially when the type is mentioned on the right:
E.g.
var firstName = new string();
is better to me than ...
string firstName = new string();
... because why do I need to say string firstName when I know it's a string based on the right hand instantiation? Of course, once again this is subjective.
Standards and using code analysis tools coupled with code reviews can really make a difference though.
Here's a list of good analysis tools: http://en.wikipedia.org/wiki/List_of_tools_for_static_code_analysis
Assembler fits the bill of "a language where the bad things to do are either actively discourage or just outright difficult" - having your program segfault at runtime is rather discouraging, and writing badly structured web software in assembler would be outright difficult.
I think an aspect of a language / framework that isn't often talked about is the community around it.
I think Rails does a great job of encouraging better practices not only in the technology itself - which is very much focused on good practices eg. creation of unit tests when you generate scaffolding, but in the community which encourages best practices etc
Boo language for the same reasons as Python.
Maybe I'm a bit biased...?
精彩评论