Hidden Features of PHP? [closed]
Asked Answered
F

78

174

I know this sounds like a point-whoring question but let me explain where I'm coming from.

Out of college I got a job at a PHP shop. I worked there for a year and a half and thought that I had learned all there was to learn about programming.

Then I got a job as a one-man internal development shop at a sizable corporation where all the work was in C#. In my commitment to the position I started reading a ton of blogs and books and quickly realized how wrong I was to think I knew everything. I learned about unit testing, dependency injection and decorator patterns, the design principle of loose coupling, the composition over inheritance debate, and so on and on and on - I am still very much absorbing it all. Needless to say my programming style has changed entirely in the last year.

Now I find myself picking up a php project doing some coding for a friend's start-up and I feel completely constrained as opposed to programming in C#. It really bothers me that all variables at a class scope have to be referred to by appending '$this->' . It annoys me that none of the IDEs that I've tried have very good intellisense and that my SimpleTest unit tests methods have to start with the word 'test'. It drives me crazy that dynamic typing keeps me from specifying implicitly which parameter type a method expects, and that you have to write a switch statement to do method overloads. I can't stand that you can't have nested namespaces and have to use the :: operator to call the base class's constructor.

Now I have no intention of starting a PHP vs C# debate, rather what I mean to say is that I'm sure there are some PHP features that I either don't know about or know about yet fail to use properly. I am set in my C# universe and having trouble seeing outside the glass bowl.

So I'm asking, what are your favorite features of PHP? What are things you can do in it that you can't or are more difficult in the .Net languages?

Fluster answered 14/9, 2008 at 15:21 Comment(3)
Broken OO paradigm? For me it's the worst "hidden" feature you discover.Collbaith
These threads are kind of funny... Because for the team I work with "hidden feature" is a code phrase meaning "bug". And you know what... Sometimes discovering a hidden feature is not necessarily a good thing...Lorianne
@Ganesh one man's bug is another mans hidden feature...Tropical
H
328

Documentation. The documentation gets my vote. I haven't encountered a more thorough online documentation for a programming language - everything else I have to piece together from various websites and man pages.

Hypersonic answered 14/9, 2008 at 15:21 Comment(14)
I agree. Being able to type www.php.net/function_name and getting a reference most of the time is great.Helmer
eh, I like the manual and all but it would be nicer if everything was not just global. Not to mention some of the function names are so arbitrary its sometimes hard to find what you want.Fluster
Most IDEs have a manual look up function. In my IDE (PhpDesigner) if you type a function name and type in (), it shows you the arguments it expects in a tooltip. If you select a function and press f1 it shows the manual page for that function in the .chm fileTriazine
This is a great feature of PHP, but I wouldn't really call it hidden... If you've ever googled for method parameters, etc, you would end up at php.net.Hibernicism
True; However, the question I answered was titled "What are your favorite PHP langauge features?" and the documentation certainly applies to those criteria.Hypersonic
I agree as well. The greatest thing about the manual are the user comments. I have rarely seen other documentations have those. They can contain real gems. The only downside is that IMHO they a pruned little too soon.Soniferous
I would appreciate if they organized the function reference a bit better and divided it into topics. Especially the classes related to specific databases and other outside technologies should be separated, because they're rarely used and there's a lot of 'em.Respondent
MSDN is an extensive and largely superb reference (when including the HOWTOs and guides). It shocks me that regardless, documentation is what php devs believe is the most superior feature of php.Modeling
@Phoexo "little bit less read-able" ??? I never understanded and will never understand MSDN, while PHP docs are easy and clear.Desma
PHP's are easy and clear, no doubt about that, but MSDN is also a good source of information and will answer most of your questions.Chery
The comments system is amazing; I wish Sun had this for their online Javadocs, although there is Docjar (but would be better on the Sun website due to more visitors).Frodi
@wallacoloo the question I answered was titled "What are your favorite PHP langauge features?" and the documentation certainly applies to thatHypersonic
Disagree. The only reason the documentation is "good" is because of some of the user comments plugging all the holes in the official notes.Fikes
Yeah, PHP's documentation is good because it covers most of the 9000 edge cases of each function, and even more is covered in the comments.Zincograph
W
179

Arrays. Judging from the answers to this question I don't think people fully appreciate just how easy and useful Arrays in PHP are. PHP Arrays act as lists, maps, stacks and generic data structures all at the same time. Arrays are implemented in the language core and are used all over the place which results in good CPU cache locality. Perl and Python both use separate language constructs for lists and maps resulting in more copying and potentially confusing transformations.

Winnipegosis answered 14/9, 2008 at 15:21 Comment(15)
The advantage with Perl's approach is that we can declare our intent to have an ordered container.Sturrock
PHP array elements are ordered.Winnipegosis
My initial move from PHP to C# almost killed me. In C#, arrays are just a simple structure with a static size and numeric index. In PHP, arrays are the duct tape of the universe!Coulisse
Indeed, the flexibility of PHP arrays as well as the interfaces ArrayAccess and Iterator and Countable (to create a class that can be used exactly like an array) make my life so easy where as doing some tasks are harder without.Lapp
The versatility of arrays is hard to under-estimate. Once you develop a mindset to take advantage of them, you can do some amazing things.Destroyer
I also agree. When playing with Java for a Uni assignment, I was stunned at how rigid they were, no flexibility at all. Really made me appreciate just how good PHP arrays are.Defendant
You can even easily convert between arrays and objects by doing (array) $object and (object) $array. It's not recursive, but it's not difficult to write a function that is.Respondent
Comparing php array to java arrays is like comparing apples with bananas. If you need fast and fixed size collections, use an array. If you need growing and easy to use collections, use a List.Orlan
I'm sure php arrays are great, but 40 votes for the comment that knocks C# arrays? If a C# array doesn't fit the need, there are many options. ArrayList and generic collections are both very powerful. There are numerous types of collections for specific needs. The only actual advantage of php in this regard is that it doesn't provide any options from which a programmer must decide. You either use array or you don't have an indexable variable.Modeling
On the other hand, the syntax for arrays completely sucks. In many scripting languages you can create a simple 2D array like so: [[1, 2], [3, 4]], compare this to the PHP version: array(array(1, 2), array(3, 4)).Weissman
@gWiz: agreed. Not clear why C#'s array gets dinged for not also being an ArrayList, Dict or HashTable. Just because it works that way in one language doesn't mean it should everywhere else. That said, I used to curse ASP every time I had to switch back from PHP for much the same reason.Zumstein
@Zumstein C#'s arrays get dinged because you have to think. You just said there are 4 datatypes which are needed to cover most of the abilities of PHP's plain-ole arrays. PHP arrays just work.Malonis
You're comparing static and dynamic languages and complaining that you don't get the benefits of a dynamic language with a static language without considering the downsides to dynamic languages. I fall into the dynamic language camp and much prefer PHP's approach, but it doesn't make it The One True Way.Zumstein
I'm not sure people are knocking C# arrays. I had the same problem (still do) in which that when I went from PHP to C#, I was in the mindset that arrays are truly used for everything. But in C#, the array is just an array. It was just the culture shock rather than hating on C#.Footie
…it's not about knocking C# arrays, but I upvoted for "In PHP, arrays are the duct tape of the universe!"Deflect
H
167

Stream Handlers allow you to extend the "FileSystem" with logic that as far as I know is quite difficult to do in most other languages.

For example with the MS-Excel Stream handler you can create a MS Excel file in the following way:

$fp = fopen("xlsfile://tmp/test.xls", "wb");
if (!is_resource($fp)) { 
    die("Cannot open excel file");
}

$data= array(
    array("Name" => "Bob Loblaw", "Age" => 50),  
    array("Name" => "Popo Jijo", "Age" => 75),  
    array("Name" => "Tiny Tim", "Age" => 90)
); 

fwrite($fp, serialize($data));
fclose($fp);
Helmer answered 14/9, 2008 at 15:21 Comment(8)
I believe that the KIO framework lets you do this as well, but that's only available for KDE-based desktop applications.Malvern
IMHO having a proper OO approach would be much more sensible than this mess with stream handlers. Yes, its cute to be able to read/write Excel files, but does it have to work like this?Purlieu
Maybe so, but this approach encapsulates complexity in an interface that's common to most PHP developers... without requiring them to learn Object Oriented concepts which might be beyond them.Helmer
If you're working with Amazon S3, check out Zend_Amazon_S3, which provides a stream interface for urls like 's3://{bucket-name}/path'.Hemihedral
I've used this to create a simple DSL for my view layer by just reading the PHP file, doing some string replacement and passing it trough eval(). Eg, I made it such that I can use short-tags whenever I choose to and do @->someVar so I can access view-level data.Smelly
not a php coder but isn't this code snippet missing closing brackets for the middle three array( lines?Prussianism
Some streams are available for pop and imap too. Really killer!Emerick
@Allain Lalonde: I don't think anybody who can't grasp the concept of OOP should be writing code of this complexity. Also, how does this method combine with other stream handlers? What if I wanted to upload that XLS file via ftp://?Roundsman
M
131

Magic Methods are fall-through methods that get called whenever you invoke a method that doesn't exist or assign or read a property that doesn't exist, among other things.

interface AllMagicMethods {
    // accessing undefined or invisible (e.g. private) properties
    public function __get($fieldName);
    public function __set($fieldName, $value);
    public function __isset($fieldName);
    public function __unset($fieldName);

    // calling undefined or invisible (e.g. private) methods
    public function __call($funcName, $args);
    public static function __callStatic($funcName, $args); // as of PHP 5.3

    // on serialize() / unserialize()
    public function __sleep();
    public function __wakeup();

    // conversion to string (e.g. with (string) $obj, echo $obj, strlen($obj), ...)
    public function __toString();

    // calling the object like a function (e.g. $obj($arg, $arg2))
    public function __invoke($arguments, $...);

    // called on var_export()
    public static function __set_state($array);
}

A C++ developer here might notice, that PHP allows overloading some operators, e.g. () or (string). Actually PHP allows overloading even more, for example the [] operator (ArrayAccess), the foreach language construct (Iterator and IteratorAggregate) and the count function (Countable).

Mayemayeda answered 14/9, 2008 at 15:21 Comment(12)
As useful example of what can be achieved with magic methods goto phpcodetips.blogspot.com/2008/07/domain-model-validation.htmlFadein
Disagree. This is far weaker than similar facilities in Smalltalk, Ruby & Python (and presumably it was copied from one of these)Saiz
The fact that PHP's implementation of this functionality is weaker than those other languages, doesn't make it any less useful in PHP.Helmer
__call() is great in frameworks with map domain.com/controller/method/Bans
Magic methods are also slow as hell. Use them carefully.Impresa
Slow compared to what: garfieldtech.com/blog/magic-benchmarks yes, it's slower but not appreciably so. The pipeline will play a larger role than the magic methods unless you're operating under very large loads.Helmer
Useful for view-level logic and implementing Mixins as known in Ruby, for example.Smelly
Anyone else think that magic methods are fantastically dangerous? They don't autocomplete in your IDE of choice, unless you know there's some magic then stepping through code execution by eyeball is impossible, you can end up using them by accident instead of a similarly-named non-magic method...Cult
This seems similar in effect to forward invocation in Objective-C.Modeling
And since php 5.3 "__invoke" is added to the list of magic functions.Dibb
I updated the list to include all magic methods and have added a paragraph about other methods of overloading functionality.Mayemayeda
What language that allows operator overloading does not allow overloading of those operators?Polar
D
95

The standard class is a neat container. I only learned about it recently.

Instead of using an array to hold serveral attributes

$person = array();
$person['name'] = 'bob';
$person['age'] = 5;

You can use a standard class

$person = new stdClass();
$person->name = 'bob';
$person->age = 5;

This is particularly helpful when accessing these variables in a string

$string = $person['name'] . ' is ' . $person['age'] . ' years old.';
// vs
$string = "$person->name is $person->age years old.";
Decorticate answered 14/9, 2008 at 15:21 Comment(16)
"{$person['name']} is {$person['age']} years old" works.Print
You should post that as a hidden feature, I'd vote it up :)Decorticate
"person[name] is $person[age] years old" will also work... No quotes, no braces :)Siblee
I didn't know that one. It doesn't complain that it has to assume you're not using undefined constants?Decorticate
Makes it very Javascript-y :)Lavona
@Dean if you don't use curly braces, no it doesn't complain. The [ has to immediately follow the variable name, then its contents are interpreted as a string.Lavona
$string = sprintf("%s is %d years old.", $person['name'], $person['age']);Smote
While we're on the subject: (object)array("name" => 'bob', 'age' => 5)Tommyetommyrot
@majelbstoat: Taking out the quotes would slow the script down because the PHP interpreter will look to see if 'name' and 'age' have been set with define(...). It's also a bad practice considering it'd be possible to totally flip the keys that are accessed in each case: define('age','name'); define('name','age');Conversationalist
Don't care about performance, readability is (way!) more important.Orlan
Both using arrays AND standard class is helpful for different things.Mystify
@Willi Schönborn: sure, the performance aspect may not really matter, but considering the fact that an E_NOTICE is thrown every time PHP encounters one of those, it's just plain sloppy.Seawright
@Adam Backstrom whoa, that is an object literal in PHP! You've just blown my mind.Lavona
@Conversationalist and @Frank Farmer that's not the case. With no curly braces inside the string, PHP treats what's in the braces as literal. eg: "$person[name]" is equivalent to "{$person['name']}" - PHP won't consider name to refer to a constant in either case. See Types -> Strings, under "Variable parsing" in the PHP manual.Lavona
don't use $person[name]... if you set error_reporting to E_ALL, you will see that the compiler throws a notice. Always quote string array keys: $person['name']Saliva
I can't begin to fathom why @brianreavis's comment has 23 upvotes even though he's fundamentally misunderstood variable interpolation in strings...Roundsman
W
90

Include files can have a return value you can assign to a variable.

// config.php
return array(
    'db' => array(
        'host' => 'example.org',
        'user' => 'usr',
        // ...
    ),
    // ...
);

// index.php
$config = include 'config.php';
echo $config['db']['host']; // example.org
Woolfolk answered 14/9, 2008 at 15:21 Comment(5)
@Peter VERY useful for db->localhost exception error handling.Mystify
It's convenient for setting up a quick-and-dirty config file.Seawright
Why do you return this array? If an included file contains an array it's usable at the include immediately.Stellate
@Stellate because it would be global variable and available in the whole main scope. That's quite unpleasant, this is way better.Pact
i worked on a project in Yii framework and that project have config file in which array was returned like this, now i understand why file was like this.Betimes
P
83

You can take advantage of the fact that the or operator has lower precedence than = to do this:

$page = (int) @$_GET['page'] 
  or $page = 1;

If the value of the first assignment evaluates to true, the second assignment is ignored. Another example:

$record = get_record($id) 
  or throw new Exception("...");
Postdiluvian answered 14/9, 2008 at 15:21 Comment(17)
I'm not quite convinced of this I think; even though it seems not to be error prone it's counter-intuitive, and that in itself may promote errors.Lavona
Then again, who am I to talk. I use the ternary operator a fair bit, and yet some people feel that it's an abomination!Lavona
@thomasrutter: How would you write the first example without using 'or'?Respondent
@Pies: one way is the following, quite messy code to be honest: $page = isset($_GET['page']) ? (int)$_GET['page'] : 1; // Advantage of this is no error suppression is required.Trauma
on second thoughts, since you're looking for an integer you could use instead: $page = is_int($_GET['page']) ? $_GET['page'] : 1;Trauma
The point of doing it my way is simply that it's shorter and might be easier to read. Obviously you can do the same thing in more code. Mostly I wanted to avoid writing $_GET['page'] twice.Respondent
It's worth noting that the code after or will execute if the code before or results in the numeric value 0. So semantically it may be less likely with something like $_GET['page'], but obviously the circumstance may arise and it's good to watch out for.Turgot
It's also worth noting that the or operator is a lower-precedent version of the || operator. Also, +1 because this is highly expressive and I often forget it's possible. It should be used more often, and it's absolutely clear in what it does. I don't know about how "real males" code though, so I can't comment on that.Turgot
Personally, I hesitate to use or because I don't trust everyone I work with will always be cognizant of the difference between or and ||Seawright
It should have been called thenPsychasthenia
@DisgruntledGoat, $_GET['page'] can never be an int, unless you modify $_GET in your PHP code.Shaker
@Ionuț: Yeah I guess I meant is_numeric since that checks if it's a numeric string.Trauma
using 'or throw' doesn't work, you'll get an unexcepted T_THROW error.Saliva
$page = getPage($_POST["page"]) or GTFO();Zincograph
I feel something is added to my brain luggage every time a suppressor is used... + It is better to 404 for an URL ...&page=<something_not_valid>, rather than silently swallowing it.Psychrometer
@HalilÖzgür I think that reading from $_GET is one of the legitimate uses of error suppression, but to each his own. You could just as well create a function for it.Respondent
Everybody here seems to have forgotten this gem: mysql_connect(*) or die()Transmute
M
80

__autoload() (class-) files aided by set_include_path().

In PHP5 it is now unnecessary to specify long lists of "include_once" statements when doing decent OOP.

Just define a small set of directory in which class-library files are sanely structured, and set the auto include path:

set_include_path(get_include_path() . PATH_SEPARATOR . '../libs/');`

Now the __autoload() routine:

function __autoload($classname) {
    // every class is stored in a file "libs/classname.class.php"

    // note: temporary alter error_reporting to prevent WARNINGS
    // Do not suppress errors with a @ - syntax errors will fail silently!

    include_once($classname . '.class.php');
}

Now PHP will automagically include the needed files on-demand, conserving parsing time and memory.

Monophony answered 14/9, 2008 at 15:21 Comment(7)
is spl_autoload_register() better to use?Bans
Of course! __autoload() is PHP4 but spl_autoload_register() is a non-destructive "daisy-chaining" of autoloading methods.Eggshaped
A handy feature, but the one caveat is when you find an instance of a given class, it makes it a little more difficult to hunt down the location of a class file. Explicitly defining includes at the top gives you a finite list of involved classes and their exact location.Samuelsamuela
It's a nice feature, but only to get around the situation of not having code precompiled, so it doesn't know where the class is going to be. Big downside of this is that you can't have 2 classes with the same name, even if they are in different namespaces.Snowber
@Cory: Just have __autoload keep a list of classes loaded and the files it has loaded them from.Smelly
@Jasper & @Cory: You could also use php.net/get_included_files.Cassirer
Please have a look at the PSR-0 propsal from the PHP Standards Working Group (featuring developers of ZF, Symfony, Doctrine, CakePHP, Solar, etc.) when implementing autoloading: groups.google.com/group/php-standards/web/psr-0-final-proposalWoolfolk
F
76

Easiness. The greatest feature is how easy it is for new developers to sit down and write "working" scripts and understand the code.

The worst feature is how easy it is for new developers to sit down and write "working" scripts and think they understand the code.

The openness of the community surrounding PHP and the massive amounts of PHP projects available as open-source is a lot less intimidating for someone entering the development world and like you, can be a stepping stone into more mature languages.

I won't debate the technical things as many before me have but if you look at PHP as a community rather than a web language, a community that clearly embraced you when you started developing, the benefits really speak for themselves.

Footie answered 14/9, 2008 at 15:21 Comment(1)
Definitely a good comment. Python was my first language and it was awesome, but the lack of projects I felt capable of understanding did create a barrier. With PHP I can look up pretty much anything on the documentation and figure it out...the resources available on the web are amazing.Percaline
V
76

Variable variables and functions without a doubt!

$foo = 'bar';
$bar = 'foobar';
echo $$foo;    //This outputs foobar

function bar() {
    echo 'Hello world!';
}

function foobar() {
    echo 'What a wonderful world!';
}
$foo();    //This outputs Hello world!
$$foo();    //This outputs What a wonderful world!

The same concept applies to object parameters ($some_object->$some_variable);

Very, very nice. Make's coding with loops and patterns very easy, and it's faster and more under control than eval (Thanx @Ross & @Joshi Spawnbrood!).t

Ventricular answered 14/9, 2008 at 15:21 Comment(19)
Love these! Took minutes to boggle me, years to master.Conjugated
PHP Fatal error: Call to undefined function foobar!(); Drop the $$ in front of foo();Young
Also say more under controll than "eval()" !!Lussi
#1004105 << Related question I posted last weekWavy
variable variables are actually making the code less readable and more prone to errors.Wylde
Okay... okay... this is sick. As Elzo said, less readable, messier, thus bad. This is NOT Perl.Gerladina
With more flexibility, you will have more complexity. But also more flexibility :)Ventricular
And people really use this? Man i'd hate to read these sources.Laughter
Variable variables are one of the worst features PHP offers.Hemihedral
often messy, but in very few cases really good helpCountermove
9 Out of 10 times variable variables are better replaced with arrays so you have all the data in one place, you can iterate over it et cetera. Only in some very specific circumstances might they be useful.Smelly
Please dont make newbies use that "feature".Orlan
Variable variables are essentially double pointers. Variable functions functions are just function pointers. The concepts has been around for years since C.Impresa
@Alex - Yeah, except in PHP, newbies may use it and accept user input, which in turn causes me having to help these f'ers.Nuncupative
call_user_func() is another possible substitute for some uses of variable functions.Seawright
Please at a minimum write ${$a}. Just so the rest of us knows that something is going on, and the two $$ are not just collapsed into one.Crib
I don't know much about PHP, but implementing references (or using them if they already exist) would be way better than doing it this way.Lindsay
What on earth can you use this for? Could someone explain it?Fibrilla
@Emil, calling a template whose name is stored in a database would be one example.Conceptionconceptual
B
68

You can use functions with a undefined number of arguments using the func_get_args().

<?php

function test() {

    $args = func_get_args();
    echo $args[2]; // will print 'd'
    echo $args[1]; // will print 3
}

test(1,3,'d',4);

?>
Bistoury answered 14/9, 2008 at 15:21 Comment(1)
Was just about to post this. Sort of like the arguments property in JS functions.Bans
B
67

I love remote files. For web development, this kind of feature is exceptionally useful.

Need to work with the contents of a web page? A simple

$fp = fopen('http://example.com');

and you've got a file handle ready to go, just like any other normal file.

Or how about reading a remote file or web page directly in to a string?

$str = file_get_contents('http://example.com/file');

The usefulness of this particular method is hard to overstate.

Want to analyze a remote image? How about doing it via FTP?

$imageInfo = getimagesize('ftp://user:[email protected]/image/name.jpg');

Almost any PHP function that works with files can work with a remote file. You can even include() or require() code files remotely this way.

Bethink answered 14/9, 2008 at 15:21 Comment(4)
This is so nice! To do this in for example Java you need to include a gazillion jar files and than write a lot of boilerplate code.Stereochemistry
"You can even include() or require() code files remotely this way." Of course, include()ing a file on a server you don't control is a terrible, terrible idea.Seawright
@Frank - yes, well, one would presume that you would be including code from a server you did control.Bethink
Point being, remote file inclusion is a common PHP security issue: en.wikipedia.org/wiki/Remote_File_Inclusion#PHP .Seawright
L
63

strtr()

It's extremely fast, so much that you would be amazed. Internally it probably uses some crazy b-tree type structure to arrange your matches by their common prefixes. I use it with over 200 find and replace strings and it still goes through 1MB in less than 100ms. For all but trivially small strings strtr() is even significantly faster than strtolower() at doing the exact same thing, even taking character set into account. You could probably write an entire parser using successive strtr calls and it'd be faster than the usual regular expression match, figure out token type, output this or that, next regular expression kind of thing.

I was writing a text normaliser for splitting text into words, lowercasing, removing punctuation etc and strtr was my Swiss army knife, it beat the pants off regular expressions or even str_replace().

Lavona answered 14/9, 2008 at 15:21 Comment(6)
It's probably faster because it does single character replacements.Destroyer
strtr() does not just do single-character replacements. It can replace arbitrary-length substrings with other arbitrary-length substrings, and it still seems really fast.Lavona
You mentioned it was faster than strtolower in some cases, can you prove it? I did a small benchmark and found it to be false.Arbitrary
I found that on small strings of say 80 characters it was slower than strtolower, and on large strings of say 1MB it was faster. There's probably some fixed cost type overhead each time it's called. I was simply using strtr($this->string, 'ABCDEFGHIJKLMNOPQRSTUVWXYZ', 'abcdefghijklmnopqrstuvwxyz'); The string I was operating on was some typical English text ("The quick brown fox", that sort of thing).Lavona
I just read this post and then did some Google searching and found: simplemachines.org/community/index.php?topic=175031.0 Any idea which one is right?Forerunner
When I did testing, I found strtr to be /much/ faster for more complex replacement sets on long strings of say, 100kB in length or more. For short strings of say 80 bytes or less, I found str_replace to be much faster. I did my testing around two years ago however and I'm not sure if it's still true. I'd be surprised if strtr performance had regressed for long strings though. I believe that its performance came from doing prefix indexing before each invocation which would slow it down on short strings.Lavona
E
61

One not so well known feature of PHP is extract(), a function that unpacks an associative array into the local namespace. This probably exists for the autoglobal abormination but is very useful for templating:

function render_template($template_name, $context, $as_string=false)
{
    extract($context);
    if ($as_string)
        ob_start();
    include TEMPLATE_DIR . '/' . $template_name;
    if ($as_string)
        return ob_get_clean();
}

Now you can use render_template('index.html', array('foo' => 'bar')) and only $foo with the value "bar" appears in the template.

Equivocal answered 14/9, 2008 at 15:21 Comment(10)
and with EXTR_IF_EXISTS you get to set default values before the extractUnkind
I was going to get angry at you for suggesting extract() in any way was a good feature. But I guess that use of it is pretty handy. I suppose it's the one time I've seen it used where it's a good idea!Lavona
extract() makes it dead simple to roll your own extremely light weight templating system. +1Coulisse
Its inverse, compact(), is nice as well: $a = 1; $b = 2; compact('a', 'b'); // == array('a' => $a, 'b' => $b)Tommyetommyrot
Yes, that's probably the only really good use of extract().Destroyer
Zend Framework uses extract() a lot in their view helpers.Professionalize
I would suggest not using common words as function argument names in this case, since the $context from which you extract() could contain values at the 'as_string' or 'template_name' indexes. Using EXTR_SKIP is acceptable, but only moves the problem elsewhere (i.e. if the template is expecting an $as_string it'll get the incorrect value for it.)Respondent
extract() is evil! Almost same evil like eval() is. There is nothing worse than trying to understand and debug code using extract() and compact() in almost every function. You never know where the variable came from.Edmondson
I think extract() and compact() have their uses and can be very powerful when used in the right context. extract() is fantastic for making templating systems and compact is great for quickly building hash arrays.Nullification
Other than $as_string, this is nearly the same as my little renderView function!Psychrometer
P
52

Range() isn't hidden per se, but I still see a lot of people iterating with:

for ($i=0; $i < $x; $i++) { 
    // code...
}

when they could be using:

foreach (range(0, 12) as $number) {
    // ...
}

And you can do simple things like

foreach (range(date("Y"), date("Y")+20) as $i)
{
print "\t<option value=\"{$i}\">{$i}</option>\n";
}
Pongid answered 14/9, 2008 at 15:21 Comment(10)
you can do foreach ($array as $key=>$value) {} which is even simpler.Hellas
It might be a micro-optimization, but it's worth noting that for and while are much faster and less memory-intensive than foreach.Phenacetin
this is NOT how range() should be ever used!Hummel
You should try Python. It's as simple as "for i in range(12)", or you can use the more efficient xrange.Lindsay
I have been, that's kind of where I got the idea. I started using Python to solve Project Euler questions and its been good.Pongid
@SilentGhost: you'd still need an array to start with, which isn't always the case. @Newbie: elaborate please?Carborundum
FYI, foreach can be as fast if not faster than for under certain circumstances in PHP 5.3.Androcles
@Hellas this is what i use. Whenever i go over to java i always have to look up how to use foreach in there as well. It like foreach 10x better than a for loop. For loops are so 1970s.Outpoint
@flexxy, appartently, it's NOT. Consider this: phpbench.com scroll down to Read Loop.Shippee
@Shippee And then, check out the modify example which states "Proof in this example shows how functionally murderous the foreach() loop can be.".Phenacetin
E
44

PHP enabled webspace is usually less expensive than something with (asp).net. You might call that a feature ;-)

Embed answered 14/9, 2008 at 15:21 Comment(3)
It's also much cheaper to set up multiple servers if you don't have to pay for Windows Server on every one.Malvern
Only place I know of where Windows is cost effective is at a University that gets STEEEEP discounts on the server software in as much as it is cheaper for my dept to buy 100 copies of windows than it is to train our admins on linux (which partially makes me sad but their windows setup is clean and well setup).Lapp
For now, but you have to make the switch only once, while you'll have to buy new licences sooner or later...Anguiano
L
42

The static keyword is useful outside of a OOP standpoint. You can quickly and easily implement 'memoization' or function caching with something as simple as:

<?php
function foo($arg1)
{
    static $cache;

    if( !isset($cache[md5($arg1)]) )
    {
        // Do the work here
        $cache[md5($arg1)] = $results;
    }

    return $cache[md5($arg1)];
}
?>

The static keyword creates a variable that persists only within the scope of that function past the execution. This technique is great for functions that hit the database like get_all_books_by_id(...) or get_all_categories(...) that you would call more than once during a page load.

Caveat: Make sure you find out the best way to make a key for your hash, in just about every circumstance the md5(...) above is NOT a good decision (speed and output length issues), I used it for illustrative purposes. sprintf('%u', crc32(...)) or spl_object_hash(...) may be much better depending on the context.

Lapp answered 14/9, 2008 at 15:21 Comment(4)
Just a copied feature from C/C++Abdul
@Abdul I don't think anyone would deny that almost all of PHP has been copied from C, C++, Perl, etc.Seawright
Copying is the best thing that can be done.Mayemayeda
Bad PHP. It's always copying features from others. It should write everything from scratch instead! (In case of the slightest possibility of this being taken seriously: I'm joking)Psychrometer
G
42

One nice feature of PHP is the CLI. It's not so "promoted" in the documentation but if you need routine scripts / console apps, using cron + php cli is really fast to develop!

Godevil answered 14/9, 2008 at 15:21 Comment(2)
I should really look into this, I have several cron jobs that fetch a PHP script through wget http://example.com...Trauma
CLI is also an excellent way to spot-debug, as warnings/errors will show without you having to change your error reporting preferences.Chacma
A
39

Then "and print" trick

<?php $flag and print "Blah" ?>

Will echo Blah if $flag is true. DOES NOT WORK WITH ECHO.

This is very handy in template and replace the ? : that are not really easy to read.

Alexisaley answered 14/9, 2008 at 15:21 Comment(8)
I myself find the ternary operator much more obvious than exploiting the evaluation short-cirtcuit of a logical and.Banting
Actually that's the same number of characters as <?php if($flag) print "Blah"Zizith
Parenthesis are not as easy to type as "and", especially on my bloody french keyboard ;-)Anguiano
This is shorter, assuming you have shorttags enabled: <?=$flag?'blah':''?>. Actually without shorttags it's still shorter.Trauma
@all comments - This isn't about how short you can get it! It's about readability and ease of use for template people, who sometimes are not even programmers.Nuncupative
I would comment that the if () statement is easier and more readable. It's certainly easier for me to get my head around than exploiting essentially a side effect of the 'and' operator in PHP, where it's easy to make a mistake (or look like it's a mistake when you read the code later). For instance, as stated this won't work the way you want with 'echo'. With if () there aren't gotchas like this.Lavona
print is a function, echo is a statement -- hence the reason echo won't work.Marimaria
if... version doesn't make me think.Psychrometer
B
37

You can use minus character in variable names like this:

class style
{
  ....
  function set_bg_colour($c)
  {
    $this->{'background-color'} = $c;
  }
}

Why use it? No idea: maybe for a CSS model? Or some weird JSON you need to output. It's an odd feature :)

Bathroom answered 14/9, 2008 at 15:21 Comment(4)
Does that work with method names? Could be useful for frameworks which use a router and I want domain.com/something-with-minuses/view/Bans
The curly braces allow you to access object properites that have dashes, dots, and other non-alphanumeric entities. One reason to use it is when dealing with xml, where the entity names can be dotted like in NITF/NewsML <body.content>. If you use SimpleXML, you would access it like this $item->DataContent->body->{'body.content'}.Cabanatuan
PHP variables can take any characters when used that way, even spaces and newlines.Hummel
This would be very useful when using in SimpleXML... awesome. Thanks for sharing.Counselor
S
34

HEREDOC syntax is my favourite hidden feature. Always difficult to find as you can't Google for <<< but it stops you having to escape large chunks of HTML and still allows you to drop variables into the stream.

echo <<<EOM
  <div id="someblock">
    <img src="{$file}" />
  </div>
EOM;
Soane answered 14/9, 2008 at 15:21 Comment(7)
HEREDOC is my favorite way to build and use SQL statements.Wingo
Note: the closing EOM; cannot be indented.Koodoo
Good, but pointless if you use templates. Plus it gets in the way of proper indentation.Huneycutt
Dear god, that is the ugliest piece of code I have ever seen. If you're using HEREDOC's, then you haven't separated presentation from logic.Paregmenon
@Byron: You don't have to use it for presentation, it can be used for any string. See the comment from bdl.Ugric
@bdl: I've used heredocs for SQL statements, but stored procedures tend to be more maintainable, in my opinion.Varied
It would be much better to separate HTML, Javascript from PHP using MVC pattern. )Joselynjoseph
V
34

Probably not many know that it is possible to specify constant "variables" as default values for function parameters:

function myFunc($param1, $param2 = MY_CONST)
{
//code...
}

Strings can be used as if they were arrays:

$str = 'hell o World';
echo $str; //outputs: "hell o World"

$str[0] = 'H';
echo $str; //outputs: "Hell o World"

$str[4] = null;
echo $str; //outputs: "Hello World"
Vermicide answered 14/9, 2008 at 15:21 Comment(6)
That last one is nifty. Though I have no idea when it would be better than some other method of removing a character. +1 nonthelessFluster
It's probably more efficient than calling a function to do it. Strings are normally stored contiguously in memory, so getting to $str[4] is trivial. Storing strings as arrays of characters is common to most languages that derive from C.Wavy
You don't have to use a defined constant as a default value. The following is also perfectly valid: function foot($param1, $default = array('key'=>'value'), $default_s = 'String', $default_i = 10, $default_b = false). However you are correct in noting you can't use a variable as a default argument.Lapp
@Lapp Your example is perfectly valid since array() is not a function but a language construct. Function calls are not allowed as default values for arguments.Bicollateral
you can also access a string char like this: $a_char=$a_string{2}Laflam
Be careful with treating strings as arrays if you have multi-byte strings (foreign languages, etc.)Cunha
P
33

The single most useful thing about PHP code is that if I don't quite understand a function I see I can look it up by using a browser and typing:

http://php.net/function

Last month I saw the "range" function in some code. It's one of the hundreds of functions I'd managed to never use but turn out to be really useful:

http://php.net/range

That url is an alias for https://www.php.net/manual/en/function.range.php. That simple idea, of mapping functions and keywords to urls, is awesome.

I wish other languages, frameworks, databases, operating systems has as simple a mechanism for looking up documentation.

Pointed answered 14/9, 2008 at 15:21 Comment(2)
range() can be useful for foreach( range(1, 10) as $i) { };Bans
If you have FireFox; just type PHP function in the address bar it will do a Google 'I'm feeling lucky' search and you almost always end up on the right php documentation page.Visigoth
D
30

Fast block comments

/*
    die('You shall not pass!');
//*/


//*
    die('You shall not pass!');
//*/

These comments allow you to toggle if a code block is commented with one character.

Deposit answered 14/9, 2008 at 15:21 Comment(5)
This isn't really specific to PHP. This works in any language that supports // ... line comments and /* ... */ block comments.Britanybritches
any code cleanup utilities end up hating you for using this... ;)Mystify
I've also used /** / before and /**/ after. You can toggle the block by removing and adding the space in the first. This has an added benefit of working with CSS (and other languages that do not support // ... comments).Moniquemonism
FWIW, link to the original article aleembawany.com/2009/01/27/lazy-block-comment-trickDisastrous
@aleemb, refrain from making any further edits to this question.Phonography
T
29

My list.. most of them fall more under the "hidden features" than the "favorite features" (I hope!), and not all are useful, but .. yeah.

// swap values. any number of vars works, obviously  
list($a, $b) = array($b, $a);

// nested list() calls "fill" variables from multidim arrays:  
$arr = array(  
  array('aaaa', 'bbb'),  
  array('cc', 'd')  
);  
list(list($a, $b), list($c, $d)) = $arr;  
echo "$a $b $c $d"; // -> aaaa bbb cc d  

// list() values to arrays  
while (list($arr1[], $arr2[], $arr3[]) = mysql_fetch_row($res)) { .. }  
// or get columns from a matrix  
foreach($data as $row) list($col_1[], $col_2[], $col_3[]) = $row;

// abusing the ternary operator to set other variables as a side effect:  
$foo = $condition ? 'Yes' . (($bar = 'right') && false) : 'No' . (($bar = 'left') && false);  
// boolean False cast to string for concatenation becomes an empty string ''.  
// you can also use list() but that's so boring ;-)  
list($foo, $bar) = $condition ? array('Yes', 'right') : array('No', 'left');

You can nest ternary operators too, comes in handy sometimes.

// the strings' "Complex syntax" allows for *weird* stuff.  
// given $i = 3, if $custom is true, set $foo to $P['size3'], else to $C['size3']:  
$foo = ${$custom?'P':'C'}['size'.$i];  
$foo = $custom?$P['size'.$i]:$C['size'.$i]; // does the same, but it's too long ;-)  
// similarly, splitting an array $all_rows into two arrays $data0 and $data1 based  
// on some field 'active' in the sub-arrays:  
foreach ($all_rows as $row) ${'data'.($row['active']?1:0)}[] = $row;

// slight adaption from another answer here, I had to try out what else you could  
// abuse as variable names.. turns out, way too much...  
$string = 'f.> <!-? o+';  
${$string} = 'asdfasf';  
echo ${$string}; // -> 'asdfasf'  
echo $GLOBALS['f.> <!-? o+']; // -> 'asdfasf'  
// (don't do this. srsly.)

${''} = 456;  
echo ${''}; // -> 456  
echo $GLOBALS['']; // -> 456  
// I have no idea.  

Right, I'll stop for now :-)


Hmm, it's been a while..

// just discovered you can comment the hell out of php:
$q/* snarf */=/* quux */$_GET/* foo */[/* bar */'q'/* bazz */]/* yadda */;

So, just discovered you can pass any string as a method name IF you enclose it with curly brackets. You can't define any string as a method alas, but you can catch them with __call(), and process them further as needed. Hmmm....

class foo {
  function __call($func, $args) {
    eval ($func);
  }
}

$x = new foo;
$x->{'foreach(range(1, 10) as $i) {echo $i."\n";}'}();

Found this little gem in Reddit comments:

$foo = 'abcde';
$strlen = 'strlen';
echo "$foo is {$strlen($foo)} characters long."; // "abcde is 5 characters long."

You can't call functions inside {} directly like this, but you can use variables-holding-the-function-name and call those! (*and* you can use variable variables on it, too)

Toadinthehole answered 14/9, 2008 at 15:21 Comment(7)
Please don't overuse the ternary comparison operator; this leads to code obfuscation.Destroyer
Wow. That could totally hose your $GLOBALS list. Bad practice. Seriously.Mystify
Is there an obfuscated PHP contest yet?Paregmenon
Well, trick with swap - impressive and useful, thanks.Attraction
${''} = 456; hahaha.... quite the abuse.Sodom
+1 for ${''} = 456;. Finally a completely anonymous variable.Psychrometer
"Abuse" used correctly in your post in every sense.Transmute
S
26

I'm a bit like you, I've coded PHP for over 8 years. I had to take a .NET/C# course about a year ago and I really enjoyed the C# language (hated ASP.NET) but it made me a better PHP developer.

PHP as a language is pretty poor, but, I'm extremely quick with it and the LAMP stack is awesome. The end product far outweighs the sum of the parts.

That said, in answer to your question:

http://uk.php.net/SPL

I love the SPL, the collection class in C# was something that I liked as soon as I started with it. Now I can have my cake and eat it.

Andrew

Stateroom answered 14/9, 2008 at 15:21 Comment(0)
A
26

Array manipulation.
Tons of tools for working with and manipulating arrays. It may not be unique to PHP, but I've never worked with a language that made it so easy.

Anthropogenesis answered 14/9, 2008 at 15:21 Comment(3)
like what for example? It seems to me like the functions are all awkwardly named and positioned in the global namespace. Plus I can't think of anything thats not just as easy in another language except for maybe $arr[] = $newvalue for adding values - thats coolFluster
Well, the PHP array is a datastructure that can be used easily as a stack, queue, deque, list, hashtable, etc. It's pretty flexible indeed for most common needs, without resorting to anything else but array_* functions.Wetterhorn
Python does arrays (as lists and tuples) much better than PHP does.Zizith
D
24

I'm a little surprised no-one has mentioned it yet, but one of my favourite tricks with arrays is using the plus operator. It is a little bit like array_merge() but a little simpler. I've found it's usually what I want. In effect, it takes all the entries in the RHS and makes them appear in a copy of the LHS, overwriting as necessary (i.e. it's non-commutative). Very useful for starting with a "default" array and adding some real values all in one hit, whilst leaving default values in place for values not provided.

Code sample requested:

// Set the normal defaults.
$control_defaults = array( 'type' => 'text', 'size' => 30 );

// ... many lines later ...

$control_5 = $control_defaults + array( 'name' => 'surname', 'size' => 40 );
// This is the same as:
// $control_5 = array( 'type' => 'text', 'name' => 'surname', 'size' => 40 );
Destroyer answered 14/9, 2008 at 15:21 Comment(8)
$defaults should be $control_defaultsYellowknife
I think it's not as clear as array_merge when you have a lot of code to maintain. At least, when you use, the array_merge function, it's evident that you're dealing with arrays.Wordbook
And that fact that you're doing ... + array( ... isn't enough to point this out? :-)Destroyer
What version of PHP do you need for this?Paregmenon
This is a great feature and it should be noted that the array on the "right" side of the "+" will not over-write existing keys of the array to the "left" side of the "+".Androcles
Actually @wilmmore, it will. That's the very feature which makes it so useful.Destroyer
I think that elements found in the left hand array are those that remain, i.e., are not overwritten by those on the right. So i think size would still be 30.Commend
If you are using this as if it is array_merge, you are doing it wrong: "The + operator returns the right-hand array appended to the left-hand array; for keys that exist in both arrays, the elements from the left-hand array will be used, and the matching elements from the right-hand array will be ignored." php.net/manual/en/language.operators.array.php vs php.net/manual/en/function.array-merge.phpPsychrometer
D
21

Quick and dirty is the default.
The language is filled with useful shortcuts, This makes PHP the perfect candidate for (small) projects that have a short time-to-market. Not that clean PHP code is impossible, it just takes some extra effort and experience.

But I love PHP because it lets me express what I want without typing an essay.

PHP:

if (preg_match("/cat/","one cat")) {
   // do something
}

JAVA:

import java.util.regex.*;
Pattern p = Pattern.compile("cat");
Matcher m = p.matcher("one cat")
if (m.find()) {
  // do something
}

And yes, that includes not typing Int.

Dibb answered 14/9, 2008 at 15:21 Comment(6)
you should use strpos instead: if (false !== strpos("one cat", "cat")) {Truckload
@Truckload the purpose of his example was to illustrate and compare the running of a quick regex match, not how to find the string "cat" in "one cat".Lapp
Good call @eyelidlessness. I used ereg() for serveral years, went the preg route since php 5.3. I don't like deprecated messages ;-)Dibb
Java: if (Pattern.matches("cat", "one cat")) { // do something } Stop complaining about java if you don't know it.Orlan
+1 Willi how do you do preg_replace('/([<[]!--\s*)(\S*?)(\s*--[>]]?)/se', "\$this->Choose('\\1','\\2','\\3',\$data)", $text); in Java? This finds a comment in the input text and then calls a function with the matched elements which in this case $this->choose(...) decides what to replace the match with and returns the results.Putrefy
Regex is PHP is pretty crappy... I'd much rather have Perl or JavaScript style Regex where the // is built into the language.Hairstreak
F
21

Here's one, I like how setting default values on function parameters that aren't supplied is much easier:

function MyMethod($VarICareAbout, $VarIDontCareAbout = 'yippie') { }
Fluster answered 14/9, 2008 at 15:21 Comment(8)
Funnily enough I saw this "hidden feature" in Google Reader last week. I don't get what's hidden about it - it's basic syntax. Try if($var = true) for example.Neoteny
Easier than what? Most language have this feature.Claribelclarice
Easier than C# (and I think C++, and Java)Fluster
C++ does support default parameter values.Wavy
Real object orientated languages support overloading method names which makes this feature work the same.Orlan
c# doesn't support default values at all. you have to write an overloaded function and always declare the value which is just plain cumbersomePutrefy
C# will support default values in the 4.0 release. Albeit supposedly mostly for COM interop supportFluster
This is something I'm used to in C++ and Python. Default args are one of the things I think are omissions in some languages, not just cool features in other languages.Gerladina
L
16

You can use break N; to exit nested loops (to compensate for the lack of goto). For example

for (int i=0; i<100; i++) {
    foreach ($myarr as $item) {
        if ($item['name'] == 'abort')
            break 2;
    }
}

More info here - http://php.net/manual/en/control-structures.break.php

Lupercalia answered 14/9, 2008 at 15:21 Comment(3)
I guess that 'feature' better remains HIDDEN or we will soon have dozens of PHP 'programmers' using GOTO's. GOTO's are evil! But anyways, didn't know about that one... Nice :)Hesychast
goto actually isn't lacking anymore ...Mayemayeda
It's very helpful and safe, as long as we're not dealing with objects/structures that need to be, for a lack of a better word, "deallocated". But all in all, I really do miss this in other languages - it's much more clear and unambiguous than any GOTO could ever be, I think.Bucovina
S
16

Output buffering via ob_start() is far more useful than most realize. The first hidden feature here is that ob_start accepts a callback:

function twiterize($text) {
    // Replace @somename with the full twitter handle
    return preg_replace("(\s+)@(\w)+(\s+)", "http://www.twitter.com/${2}", $text);
}

ob_start(twiterize);

Secondly, you can nest output buffers... Using the previous example:

ob_start(parseTemplate);
 // ... 
 ob_start(twiterize);
   // ...
 ob_end_flush();
 // ... 
ob_end_flush();

Help contents, text ads, dictionary/index functionality, linkify, link-redirection for tracking purposes, templating engine, all these things are very easy by using different combinations of these 2 things.

Salome answered 14/9, 2008 at 15:21 Comment(2)
I know its lazy but I use output buffering so deep in my code I can add headers and totally avoid the headers already sent error. This is most noticeable in templating, if somewhere deep in a nested template an error occurs its simple to add a header to redirect the user to an error page.Putrefy
To expand on the post by DeveloperChris, I find it odd that most people don't realize it's a GREAT way to convert characters on the fly without having to worry about whence they came from. I type mostly Polish pages, and they need to be in ISO-8859-2. However, most simple editors only do Windows-1250. I've seen source files with, say, translation tables coded directly in 8859-2, but it's a PAIN to maintain. Drop a nice conversion buffer on top of the thing and voilla! - a huge pain gone, and the code is suddenly more readable.Bucovina
C
15

Actually, you're not quite right about that you cannot specify what types a method expects, it does work as you'd expect.

function foo ( array $param0, stdClass $param1 );

Note: This only works for 'array' and object names.

And so on, and you can even pass in your own classes as expected parameters. Calling the methods/functions with something else will result in a fatal error.

Another hint about a good intellisense in PHP. We use ZendStudio and it will actually work a lot better if you write good PHPDocs for your methods, it will look into those when hinting.

Cumbersome answered 14/9, 2008 at 15:21 Comment(5)
According to ch2.php.net/language.oop5.typehinting, "string" isn't supported for type hinting. "array" is supported from PHP 5.1 on, and specific object types are supported since 5.0.Condonation
To reinforce JW, scalar types are not supported when type-hinting (except for arrays), however all types are supported when type-casting.Lapp
I was with you until you suggested ZendStudio was an even remotely passable IDE.Fagaceous
Typehinting for scalars will be available as of PHP 5.4Mayemayeda
Also, the note reads "This only works for 'array' and object names." but to be totally pedantic about it, it should read: "This only works for 'array' and class names."Androcles
P
13

Ctype functions are faster than preg_match() for basic character validation.

ctype_alnum() — Check for alphanumeric character(s)
ctype_alpha() — Check for alphabetic character(s)
ctype_cntrl() — Check for control character(s)
ctype_digit() — Check for numeric character(s)
...etc...

Precocious answered 14/9, 2008 at 15:21 Comment(1)
Very nice - I have never heard of these, and they are enabled by default without the need for installing or configuring additional PHP modules. Can anyone posit why they're not used more often?Thirzi
B
13

Besides instant access to start coding away at anything you need for a website?

Besides magic methods and reflections, some interesting functions are:

  1. serialize / unserialize - state saving goodness via sql, cookies, processes, flatfile. good stuff.
  2. json_encode / json_decode - instant AJAX fun
  3. get_class - helpful for those weary loose-typing moments
  4. call_user_func_array - powerful when you can work with your code as strings (think dynamic)
  5. method_exists - reflection
  6. func_num_args / func_get_arg - unknown arguments ftw
  7. set_error_handler / set_exception_handler - very good debugging capabilities for a scripting language
Bullfight answered 14/9, 2008 at 15:21 Comment(1)
As a side-effect of that you have a heavily polluted global namespace.Hairstreak
M
13

Date functions. I have to handle a lot of time information and date strings all day long, so functions like strftime() and strtotime() are just awesome.

Melanie answered 14/9, 2008 at 15:21 Comment(4)
Make sure you check out DateTime. php.net/datetimeTommyetommyrot
Actually strtotime sucks, because the magic is nowehere documented and you can't use a custom format for parsing. -1Orlan
Agreed with the above comments; strtotime() is terrible, but 5.3's DateTime is much better (as you can specify the input format exactly).Hennessey
I completely disagree. Doing dates in PHP was horrid until DateTime came around.Hairstreak
B
13

a) the manual -- extremely comprehensive, up-to-date and just a huge source for inspiration while problem-solving - stuck? browse/search the manual, it'll come to you

b) arrays - they're plastic, they're associatively indexed, they can be easily nested (!) to make up some wild data structures, and there's a multitude of functions just for array operations alone. Oh, and did I mention treating separate variables as an array of values?

c) eval() and similar constructs (like dynamic variable and function names) which allow for much greater flexibility (and are still relatively safe provided you know what you're doing) - nothing beats a program that basically defines its own process flow (or even specific execution) on the fly

d) most probably the easiest thing to overlook: as almost everything in the ZEND engine is a zVal (which in essence is a collection of pointer references), the ability to return about anything as a function return value


Also, I'd like to point out one great feature, but one which is related more to PHP source than the language (and so - listed separately):

e) the ease of writing C extensions (mostly interfaces for other objects like OpenAL or SDL) - great source code structure and about as many powerfull tools on the 'inside' as there are on the 'outside' - if you ever need to expand the functionality just that little bit further.

Bucovina answered 14/9, 2008 at 15:21 Comment(3)
I've been writing PHP full time for 5 years now, and haven't encountered a single situation in which I legitimately needed to use eval() or variable variables.Seawright
Readability of eval()-using programs is ... ungood. Worse than "goto" imho, but just like "goto", might have legitimate uses.Gerladina
@Frank: extremely useful when coding with someone doing extreme GET operations (near the URI length limit). Declare a table and drive through it with automatic sanitization of inputs. Wasn't extremely needed, but it made my life that much easier. @Ivan: I will agree, it's horrible. On the other hand, there are cases where similar - and yet different - functions need to center around a common core. At one point it was much easier for me to just generate these at runtime, since the accepted standard was to declare PHP functions as external commands used by the interface. Lots of time saved.Bucovina
W
12

filter_var function. Not a hidden pearl, but pretty new.

Wylde answered 14/9, 2008 at 15:21 Comment(0)
D
12

Error suppression via the error control operator, @, should almost never be used. It promotes lazy and non-defensive coding practices by simply ignoring errors, creates debugging nightmares since errors of all types--even fatal ones--will be suppressed, and, in some cases, can cause a hit to performance (especially when suppressing large quantities of errors).

Durer answered 14/9, 2008 at 15:21 Comment(13)
I'm glad you said 'almost never'. The function fopen() is notorious for throwing a warning and returning a testable failure value when it can't open a file. The only solution is, unfortunately, to use @fopen().Destroyer
I try to avoid making over-zealous statements about anything relating to programming. I find that it always comes back to haunt us. But ya, parse_url is a hassle too ;)Durer
Yes, it is. The "hidden" part about it is that you shouldn't generally use it ;)Durer
Lots and lots of notices in the log for undefined indexes can be irritating. I usually @ any isset($anything['something']) to avoid so many notices.Bonnell
Good defensive programming isn't just ignoring the problem. Besides, you shouldn't get any notices when using isset or emptyDurer
Shadow: if you are getting lots and lots of notices its an indication of poor coding practices. Suppressing the error is a head in the sand attitude. It can come back and bite you. if a value is meant to be there and its not then its an error. if the value can be undefined then you should test for it. Security weaknesses can result otherwise.Putrefy
in some special cases you actually MUST use this operator to make code compatible with other systems/versions.Hummel
That's why I said "almost never" and not "never"Durer
@staticsan: That's not true. Use file_exists prior to attempting to perform file operations.Paregmenon
The problem with that is that file_exists() followed by fopen() isn't atomic. Sometimes that's not a problem; sometimes it is.Destroyer
@staticsan: Indeed, but it's not just fopen(). Most functions that deal with external data sources, esp. on network, have this flaw. Connecting outside the pref. environment is always risky, and about 99% of the time there's a way to test for failure one way or the other. And then there are the functions that NEITHER throw an error NOR return a testable failure result, but I can't name even one off the top of my hand (though I remember seeing at least one), so it's not all bad. Still, it's always better to have more warnings than less, and to use the @ like GOTO - with the respect it deserves.Bucovina
@Lotus Notes: I'd love to see You do a file_exists() on a remote HTTP server. :D I know, it's not encountered often, but there it is. Connecting and checking for it is usually a huge pain, but oftentimes the best plan. Unless of course, it's allowed to fail safely, and thus the @ is justified.Bucovina
Yes, there are several culprits. I mentioned only fopen() because far-and-away that's the one that I encounter the most often. I do the same belt-and-braces approach around mysql_connect(), too.Destroyer
A
10

Well, I've recently delivered my first GUI application to a paying customer - written in PHP! It gathers data from a barcode reader or from GUI pushbuttons, checkboxes, radio buttons or text fields, stores to SQLite or remote MySQL, launches other Windows apps, sends zipped XML reports as email attachments, encrypts and decrypts stored data and even plays a sound when done.

Did it with miniPHP and Winbinder. Is that hidden enough? I guess not many PHP developers have really tried this out.

Ap answered 14/9, 2008 at 15:21 Comment(3)
I'd guess that not many PHP devs have tried it out because there's little in the way of PHP connections to OS APIs.Turgot
-1, there is a reason for not trying itOrlan
+1 for doing this. I use Winbinder, PHP-GTK and a load of other stuff as well. As for the connections to OS, that's why some nifty libs exist, like php-opengl or php-openal. I know that most of this SHOULD be written in C++, but it's an interesting challenge nevertheless. And most importantly, it does AWAYYYYYY with most clutter found in "proper Windows apps" - I don't need heavy functionality and all kinds of cleverness that evolved over many years and are now "standard" - it just clutters my code up to a point where I don't recognize it any more. 3k vs 300-byte source upon creation, anyone?Bucovina
T
8

Shorthand Boolean Chains

<?php

TRUE AND print 'Hello';
FALSE OR print 'World';

// Prints "Hello World";

// Complex example...
User::logged_in() or die('Not allowed');
User::is_admin() AND print 'Admin Area';

Which is really useful if you have PHP files in a web-accessable area. By inserting this little tidbit at the top of each file you can make sure that no-one can access any file but index.php

<?php defined('YOURCONSTANT') or die('Not allowed');

///rest of your code
Tropical answered 14/9, 2008 at 15:21 Comment(1)
That would print "HelloWorld" not "Hello World".Gruel
P
8

As others have mentioned, the ability to run PHP at the command line level is fantastic. I set PHP scripts as cron jobs for data cleanup and backup purposes all the time. Just start the file with these lines:

#!/usr/bin/php5
<?php
// start coding here

Note that the first line may be different depending on where PHP is installed on your system.

From here, it's easy to implement PHP for more complex system-level processes, like daemons.

Pisistratus answered 14/9, 2008 at 15:21 Comment(4)
Alternately you can point to #!/usr/bin/env and let the system find it for you.Preeminent
It just sucks that you can't do class autoloading in CLI otherwise it's a great feature.Durable
protip: use #!/usr/bin/env php and it will be less dependent on where the php binary resides on disk.Saliva
You can also use php script.php. Not as short, but more guaranteed to work on different machines.Chacma
B
8

You can easily add an element to an array.

$my_array = array();
$my_array[] = 'first element';
$my_array[] = 'second element';

Element may be anything: object, array, scalar...

Bes answered 14/9, 2008 at 15:21 Comment(5)
He asked "...what are your favorite features of PHP?"Bes
The first line in unnecessary.Protero
Quite the opposite; the absence of that line is the source of many problems and bugs.Diatomaceous
"The first line in unnecessary" <- totally wrong! if you do not initialize the array, you can get quite a lot problems in different servers. You should ALWAYS initialize everything before use.Hummel
Not to mention that plainly declaring the array to be as such makes for a more readable code.Bucovina
A
7

Built in filters for parsing variables against specific predefined types - as well as covering the basics (int/float etc), extends to covering emails, urls and even if a variable is a valid regular expression.

http://ch2.php.net/manual/en/book.filter.php

Anarchy answered 14/9, 2008 at 15:21 Comment(0)
P
6

The ReflectionClass class provides information about a given class.

$classInfo = new ReflectionClass ('MyClass');
if ($classInfo->hasMethod($methodName))                                     
{
  $cm = $classInfo->getMethod($name);                                   
  $methodResult = $cm->invoke(null);
}

Among other things, useful to check if a method exists and call it.

Precocious answered 14/9, 2008 at 15:21 Comment(0)
C
6

Using array elements or object properties inside strings.

Instead of writing

$newVar = $ar['foo']['bar'];
echo "Array value is $newVar";

$newVar = $obj->foo->bar;
echo "Object value is $newVar";

You can write:

echo "Array value is {$ar['foo']['bar']}";
echo "Object value is {$obj->foo->bar}";
Columniation answered 14/9, 2008 at 15:21 Comment(3)
You can, but you shouldn't. Interpolated variables in strings is risky (the parsing is more complex) and harder to maintain.Destroyer
I think it's risky to write variables without braces.Columniation
@Destroyer Care to explain why it's riskier and harder to maintain? I find interpolation to be very convenient versus "foo:" . $bar style stuff. A good IDE will highlight interpolated variables as well so it's not difficult to maintain.Hairstreak
R
6

Typecasting and the ctype_* functions become important to ensure clean data. I have made extensive use of exceptions lately, which has greatly simplified my error handling code.

I wouldn't say the language has lots of killer features. (At least, I don't find much occasion to seek them out.) I like that the language is unobtrusive.

Riancho answered 14/9, 2008 at 15:21 Comment(1)
Why didn't I find out about Ctype Functions earlier? Very useful!Carborundum
M
5

Just about any file type can be included, from .html to .jpeg. Any byte string found inside bound by PHP open tags will be executed. Yes, an image of goat.se can contain all your usual utility functions. I'm guessing the internal behavior of include is to convert the input file to string, and parse for any php code.

Mailer answered 14/9, 2008 at 15:21 Comment(0)
H
5

preg_split(), array_intersect(), and array_intersect_key().

Herries answered 14/9, 2008 at 15:21 Comment(0)
D
4

I suggest using PHPUnit for unit testing, if you want to have annotations for marking your tests, and data providers, and data driven tests, and so on. Not to mention, it seems to get all the integration love when it comes to things like continuous integration (cruise control, bamboo, hudson, etc...).

PHP 5.3, it's a big jump, and it's throughly worth it in terms of language features. It maybe rough around the edges, but this is a startup and they'll be fixed up releases by the time you launch.

As far as magic methods go __invoke() alone is a big deal, but it doesn't have the reciprocal method for it, even then, paired with array_map, array_reduce, and array_filter, and some wrappers you can do some amazing functional programming.

__get, __set, and __call are really handy as well, I used these and some interface/class naming convention trickery to implement traits prior to 5.3, but now you have traits, as well.

Also have a look at the addendum library, written by derik rethans of ezComponents, and XDebug fame, it allows you to do annotations for php 5+. It's not bad, and performance is a non-issue with caching.

For profiling, you can use xdebug + webcachegrind.

The best IDE is probably the free eclipse PDT, if you use type hinting on parameters, and phpdoc comments for parameters and returns it can figure things out from those and provide you code completion. That should give you decent intellisense.

BTW, it's tempting to do all sorts of crazy string concats, or variable variables, or variable method calls, or variable class creation, do this in more than one place, that's not well documented and easy to search via regex, and you're SCREWED. Forget hard to debug, but refactoring is a major pain. This is something people rarely consider php has NO automated refactoring tools, and refactoring large code bases is VERY hard to do in php.

A few things to caution you, even if you smell the slightest bit of possibility that you might have to deal with multi-byte chars, or 'exotic' character encodings, I strongly urge you to wrap up string handling. In fact, introducing a thin layer of indirection which allows you to shim between or act as seams for testing/injectability between your code and built-ins will make your life easier. Not strictly necessary, but unless you have the benefit of foresight, it's hard to tackle internationalization or such large cross-cutting projects.

autoload, learn it and love it. Run away from hard coded require/includes, or worse, their *_once variants, they tie your hands in terms of injection, instead use an autoloader, simplest thing is to jam all your includes in a array, keyed on the class name, and the value is the file path from some root, it's fast. The wicked thing about this is that it makes testing really easy, as you've implemented a class loader, and so you can do some really neat stuff with it.

PHP 5.3 has name spaces now, jump for joy and use them like a mad man. This alone provides an opportunity to create seams (rare) for testing/injections.

Opcode caches, file accesses are slow, to avoid them, use an opcode cache, it's not just the file access, it's all the parsing, really. If you don't have to parse PER request, it makes a BIG difference. Even doing this for a front controller/interceptor will give you a lot of benefits.

Think different, one of the most troubling things for PHP programmers if they come from Java/.Net is that your application server is spread across PHP/Apache, or whatever web server you're using.

Phing/Ant/PHPMaven early on it seems easy just to jam everything in, but build scripts are still useful in php and they have some great support.

I had trouble with method overloading, and still contend with it. I came up with a pattern to alleviate a certain aspect of it. I often had many things that could fulfill a certain parameter, so when you document it @param mixed(int|array|fooObject) if those were the possibilities, I created a static method called Caster::CastTo($param, $toTypeAsString) that would just run through a case matching the type and trying to convert it to a known type. The rest of the method could then assume that one type, or a failure to convert, and work with that. And since I jammed ALL conversions in one class, it stopped mapping of types from being a cross cutting concern, and since these functions can be individually tested, I could test them once, and rely on them everywhere else.

Detention answered 14/9, 2008 at 15:21 Comment(1)
PHPUnit/PHPMaven are incompatible to 90% of common php frameworks.Orlan
A
4

The alternative syntax for control structures

There are a lot of people who don't know this syntax. When I use pure PHP for templating, this syntax offers a nice and clean way to mix simple control structures such as if or foreach with your HTML template code, usually combined with the <?= $myVar ?> short style of printing a variable.

Anticipant answered 14/9, 2008 at 15:21 Comment(5)
Not really portable, a lot of people are moving away from it.Sabayon
I actually disable this. it can break pages that start with <?xml ... it means you need to write out the string when thats unnecessaryPutrefy
wont this 'short syntax' be removed in php6?Elliellicott
@DaNieL Nope. They decided to keep it.Diatomaceous
@Commenters, There's a difference between the alternative syntax for control structures (which this post covers, e.g. if (2 + 2 === 4): echo 'hi'; endif;) and short tags (e.g. <?= 'hi' ?>).Britzka
N
4

There's lots of gems hidden in the Standard PHP Library. Array access allows you to build an object that works to an array interface but add your own functionality on top.

Also when you create an ArrayAccess object by setting a flag in the constructor you can read and write an object as either an array or an object. Here's an example:

$obj = new ArrayObject(array("name"=>"bob", "email"=>"[email protected]"),2);
$obj->fullname = "Bob Example";
echo $obj["fullname"];
$obj["fullname"]="Bobby Example";
echo $obj->fullname;
Neoteny answered 14/9, 2008 at 15:21 Comment(0)
S
4

I also like the difference between ' and ".

$foo = 'Bob';
echo 'My name is {$foo}'; // Doesn't swap the variable
echo "My name is {$foo}"; // Swaps the variable

Therefore, if your string doesn't need variable swapping, don't use a ", it's a waste of time. I see lots of people declaring strings with " all the time.

Note: I use { } as it makes my variables stand out more.

Soane answered 14/9, 2008 at 15:21 Comment(5)
Also use { } for arrays: echo "Here is {$array['bob']['name']}!"Precocious
+1 string interpolation is something many other languages lack. When moving from perl to php I breathed a sigh of relief when it worked. The only think it lacks is you can't interpolate constants. define ('FOO','bar'); echo "foo {FOO}"; doesnt work :(Putrefy
String concatenation is just as fast in PHP as variable interpolation and is easier to read and maintain.Destroyer
@staticsan: I completely disagree, I find embedding variables into the string easier to read and much easier to maintain.Dissimilar
Great for writing out HTML without having to escape anything.Paregmenon
B
4

I'm partial to the other PHP users out there. It's easy to get answers and direction when necessary.

Brow answered 14/9, 2008 at 15:21 Comment(0)
F
4

specifying implicitly which parameter type a method expects

Actually, this one is partly possible (at least in PHP5) - you can specify the type for array and object parameters for functions and methods, though you are out of luck in case of scalar types.

class Bar
{
    public function __construct(array $Parameters, Bar $AnotherBar){}
}

Apart from this one and the magic methods Allain mentioned, I also find the interfaces provided by SPL (Standard PHP library) indispensible - you can implement the necessary methods in your class, for example, I particulary like the ArrayAccess and Iterator interfaces, that allow using an object like an associative array or iterating over it just like any simple array.

Fatherhood answered 14/9, 2008 at 15:21 Comment(2)
"though you are out of luck in case of scalar types" << Yeah, totally sucks too. I work @ a mostly PHP shop, and we wanted to start writing all our PHP method/function parameters with types as a good coding practice. We ended up not doing so when we realized that we wont be able do to things like function foo(int a, int b, Bar c){}Wavy
Your example is misleading. The code you provide is doing type-casting which supports scalar types. (int)$i will return an int (and not a string representation), as well as (Bar)$i will return a Bar or failure. Type hinting is done at the function definition level (function foo($a, array $b, Bar $c)) and only supports hinting arrays and objects.Lapp
P
3

I think that their proper respect for the GOTO function is key.

https://www.php.net/goto

Preeminent answered 14/9, 2008 at 15:21 Comment(1)
The obligatory xkcd: xkcd.com/292Macle
K
3

I have started to switch over to python, and one thing I loved in python is the live interpreter. It wasn't until working on a php project later that I realized php does have this option, it's just not widely known. In a command prompt, type php -a and paste in any php code you want to test, but just remember to start it with <?php

Kalvin answered 14/9, 2008 at 15:21 Comment(1)
You don't have to type "<?php", however you will have to type "echo" or "var_dump", and don't forget the ";".Mcbride
E
3

Well, the community is in the first place for me. Whatever can your problem be, you'll always find someone who had it before and almost every time a solution... and sometimes I've seen a completely free share of ideas, ways to approach a single problem.

I'm trying to learn Python now (to grow up as... well.. programmer, can that be?) and the most useful thing of Python is the indentation. I love the PHP indentation, the $ mark for sign the variables, curly braces for loops and cycles, well, those smart things keep my code very easy to understand (even if the one who's wrote the code was little..messy up.. 'spaghetti-code', mh?)

Arrays, in PHP are pretty simple and powerful.

Databases: MySQL, Postrgee, sql; you can use almost every kind of databases.. easily.

Quick: logically depends by how is the code wrote, but usually PHP is pretty fast for small/medium application (as it lose wheel in bigger application).

Elliellicott answered 14/9, 2008 at 15:21 Comment(0)
P
2

Lambda functions

Example - sort by field in multidimension-array

function sort_by_field($field, & $data) {
    $sort_func = create_function('$a,$b', 'if ($a["' . $field . '"] == $b["' . $field . '"]) {return 0;} 
            return ($a["' . $field . '"] < $b["' . $field . '"]) ? -1 : 1;');

    uasort($data, $sort_func);
}

Anonymous functions

Anonymous functions lets you define a function to a variable. http://www.php.net/manual/en/functions.anonymous.php

Pylon answered 14/9, 2008 at 15:21 Comment(2)
create_function is soooo unelegant. Try the new PHP 5.3 syntax.Emerick
To be clear, the 5.3 syntax is the Anonymous functionsPylon
O
2

The predefined interfaces:

http://php.net/manual/en/reserved.interfaces.php

For example implementing ArrayAccess will make your object appear as an array or Iterator will allow it to be used in a foreach statement.

Unfortunately you can't use "object arrays" with the native functions that take arrays as parameters.

I also found it useful to override the __call function which allows you to dynamically create properties and methods for an object.

In my database abstraction I use this to generate functions that are named by the database column names. For example if there is a column 'name' then you can change values in it by using updateByName("foo").

Oeuvre answered 14/9, 2008 at 15:21 Comment(0)
Y
2

Let's see...

  1. Ternary operators. They work wonders for processing checkboxes in form results.

    $var = ($_POST['my_checkbox']=='checked') ? TRUE : FALSE;

  2. All of the wonderful string and array processing functions are worth trawling through. strtotime(), strlen(), and strpos() are a few of my favorites.

  3. The SimpleXML class and json_decode() function. Call a REST API or RSS feed with file_get_contents(), parse it effortlessly with one of those tools, and you're done.

Yorke answered 14/9, 2008 at 15:21 Comment(1)
I know it was just an example, but your code could have been: $var = ($_POST['my_checkbox'] == 'checked');Phelia
A
2

How extremely easy is to find PHP related things Examples, Applications, Classes, Documentation, Frameworks, etc...

All over the web, it's the easiest language to learn when going commando(by yourself), and also the one with more value for your time.

After learning PHP might put CMS with joomla, a blog with wordpress, etc....

Alethiaaletta answered 14/9, 2008 at 15:21 Comment(2)
After learning PHP hit CodeIgniter or Symfony for some improved development. They should help to make it easier to switch up to Ruby or Python in the future. If that's your goal of course.Fallen
i will add also "How extremely easy is to find PHP bad Examples", sometimes. people learn to write 'hello world' and they think they are an god programmer, and spread away suggestions that.. sometimes are not exactly goodElliellicott
M
1

Stackable unit files

<?
// file unit1.php
$this_code='does something.';
?>

<?
// file unit2.php
$this_code='does something else. it could be a PHP class object!';
?>

<?
// file unit3.php
$this_code='does something else. it could be your master include file';
require_once('unit2.php');
include('unit1.php');
?>

<?
// file main.php
include('unit1.php');
require_once('unit2.php');
require_once('unit3.php');
?>

I purposely used include and require_once interchangeably to show what can be done, because they work differently.

There are multiple ways to construct your code or add files into your code. It is even possible to link HTML, AJAX, CSS, JAVASCRIPT, IMAGES and all sorts of files into your code dynamically.

I especially like it, because there are also no requirements of placing the includes/requires at the beginning, middle or end. This allows for more freedom, depending on the use.

Mystify answered 14/9, 2008 at 15:21 Comment(0)
M
1

Lot already said about this.

Just to add that one thing that looked pretty forgotten, if not hidden, is http://talks.php.net part of the http://www.php.net. It collects lot of useful presentations, some really old, but some new and extremely valuable.

Manipulator answered 14/9, 2008 at 15:21 Comment(0)
E
1

My revelations over the years have been more conceptual than language based.

1: Rendering instead of echoing.

function render_title($title){
     return "<title>$title</title";
}

so much easier to use the parts repeatably and pass them to templates when you are rendering your output instead of using echos (in which case you'd have to rely on output buffering).

2: functional programming, or at least as close as I can move towards it, functions without side-effects. Rendering, not using globals, keeping your functions to having a local scope, things like that. I thought that object oriented programming was the way to go with php for a while there, but the reduction in overhead and syntax complexity that I experienced from dropping down from object oriented methods to functional programming methods in php makes functional programing the clear choice for me.

3: Templating systems (e.g. smarty). It's taken me a long time to realize that you -need- a templating system inside what is already a template scripting language, but the seperation of logic from display that it gives you is so, so necessary.

Exieexigency answered 14/9, 2008 at 15:21 Comment(0)
L
1

In PHP5.3 you can place PHAR archives inside PHAR archives! Like WAR/EJB in the java world.

Looney answered 14/9, 2008 at 15:21 Comment(0)
Y
1

The json_encode/decode functions in php are pretty useful, though not very hidden.

Young answered 14/9, 2008 at 15:21 Comment(0)
N
1

Definitely the magic and overloading methods. Allain cited __get(), __set(), __call() and __toString(), but I also love __wakeup() and __sleep().

This magic methods are called when the object is serialized (sleep) and deserialized (wakeup). This feature ables making things like serializable Database-wrappers, which i am using in an application:

Class Connection {
   private $dsn;
   private $connection;
   ...
   public __wakeup() {
      $this->connection = ADONewConnection();
   }
}

In this way i can "save" connections in $_SESSION, etc.

Nernst answered 14/9, 2008 at 15:21 Comment(0)
B
1

GOOD:

  • The wide aceptance of PHP in WebHosting. Nearly every web-hosting service has PHP support.
  • Simple things can be solve with simple code. No classes or namespaces are strictly required.

BAD:

  • There is a ton of functions without any naming-convention. It is so hard to remember all these functions to use it effectively.
  • Bad coding habits, all over the web :(
Bastard answered 14/9, 2008 at 15:21 Comment(3)
Agree on Bad #1, but surely Bad #2 is not a fault of the language, it's a fault of the programmer? It is possible to write beautiful PHP... honest!Bollen
I think what annoys me more than the inconsistent naming is the inconsistent ordering of arguments. For example string search functions - does haystack or needle come first? In some functions the order changed a long while back - also some functions accept them in either order for compatibility.Lavona
Not sure how these are hidden features of PHP...Urinal
S
0

Using cURL to set up a test suite to drive a large, complex web form and its back end application. The tests were exhaustive - at least in terms of executing every combination of acceptable inputs.

Stonwin answered 14/9, 2008 at 15:21 Comment(0)
M
0

Question about the original post: Why do you need a switch statement in order to overload a method in PHP? Maybe you mean something by the term "overload" that doesn't match what I learned from C++.

As for favorite features of PHP, I like the Exception object. I find that having a standard error container makes it much easier to decouple the presentation logic from the business logic, and the throw/catch syntax makes it much easier to write automated tests for each class in isolation.

Malefic answered 14/9, 2008 at 15:21 Comment(1)
Too bad most PHP functions are not using exceptions!Mcbride
T
0

Magic method __callStatic.

Really useful to make singletons, like this PDO singleton class

Topcoat answered 14/9, 2008 at 15:21 Comment(0)
F
0

Another nice feature is copy(). This function makes it possible to get a file from any place(even urls work) and copy it to a local resource. So grabbing files becomes really easy.

Foushee answered 14/9, 2008 at 15:21 Comment(0)
C
0

This is great:

//file page_specific_funcs.inc

function doOtherThing(){

}

class MyClass{

}

//end file

//file.php

function doSomething(){
  include("page_specific_funcs.inc");

  $var = new MyClass(); 

}
//end of file.php

"page_specific_funcs.inc" file is only included if doSomething gets called. The declaration of classes, funcs, etc., inside methods works perfectly.

Chiles answered 14/9, 2008 at 15:21 Comment(2)
thats a -1 for PHP because lazy-loading should be handled by the container/environment.Orlan
I hate code like that. It's a nightmare to change or extend as it's completely impossible to figure out dependencies. (At least for large projects).Stereochemistry
C
-1

the hidden features that I love from php: 1. easy to learn (also easy to missused it .. ie: bad programming habits. like you can type $something = "1" ; and then you did $something += 3 ; and suddenly $something becomes an integer .. without error message/freaking exceptions, like those in java)

  1. lots of library. go to phpclasses.org and I almost got everything from there.
  2. lots of web using it. Love it or hate it .. that's the fact ! :)
  3. simple, small and easy to maintenance. you just install xampplite + vim (my favourite) on your portable devices.
  4. cheap !!! as cheap as a beer ... for example: hosting. compared to java or .net host, php host really cheap and you can get free one from some websites (although they will put some banners / hidden thing inside your website)
  5. the documentation for php was very good !! that's the main reason i am stick to php for about 6 years (although I did some projects using Groovy/Grails)
Citarella answered 14/9, 2008 at 15:21 Comment(0)
I
-2

You can set a check on every option when use switch statement, this is an example:

$check = "HELLO";

switch ($check) {
       case (eregi('HI', $check)):
             echo "Write HI!";
       case (eregi('HELLO', $check)):
             echo "Write HELLO!";
       case (eregi('OTHER', $check)):
             echo "Write OTHER!";
}

Bye...

Inadmissible answered 14/9, 2008 at 15:21 Comment(1)
You know that ereg* is deprecated, right?Lippi
D
-4

Boolean casting, which is particularly helpful for redwall_hp's first example, above.

Instead of:

$var = ($_POST['my_checkbox']=='checked') ? TRUE : FALSE;

You can type:

$var = !!($_POST['my_checkbox']=='checked');
Disuse answered 14/9, 2008 at 15:21 Comment(3)
Why doesn't $var = ($_POST['my_checkbox'] == 'checked') work?Trauma
I think the point that submitter wanted to make was something like: $var = !!($othervar - 1); -- testing if $othervar is 1, and setting bool. There are other legitimate uses where you want to force storing a boolean and where this is the easiest way to get one.Gerladina
you realize that using !! is the same as not using the ! operator at all, right? It's like saying "not not true", instead of just saying "true"Saliva
C
-5

As far as i know, you can Implicit parameter type in function call:

function getInt(int $v)
{
     echo $v;
}

getInt(5); // will work
getInt('hello'); // will fail
Cichlid answered 14/9, 2008 at 15:21 Comment(1)
You should check the manual before you post: "Type Hints can only be of the object and array (since PHP 5.1) type. Traditional type hinting with int and string isn't supported." (php.net/manual/en/language.oop5.typehinting.php)Hairstreak

© 2022 - 2024 — McMap. All rights reserved.