⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 array.c

📁 php-4.4.7学习linux时下载的源代码
💻 C
📖 第 1 页 / 共 5 页
字号:
/*    +----------------------------------------------------------------------+   | PHP Version 4                                                        |   +----------------------------------------------------------------------+   | Copyright (c) 1997-2007 The PHP Group                                |   +----------------------------------------------------------------------+   | This source file is subject to version 3.01 of the PHP license,      |   | that is bundled with this package in the file LICENSE, and is        |   | available through the world-wide-web at the following url:           |   | http://www.php.net/license/3_01.txt                                  |   | If you did not receive a copy of the PHP license and are unable to   |   | obtain it through the world-wide-web, please send a note to          |   | license@php.net so we can mail you a copy immediately.               |   +----------------------------------------------------------------------+   | Authors: Andi Gutmans <andi@zend.com>                                |   |          Zeev Suraski <zeev@zend.com>                                |   |          Rasmus Lerdorf <rasmus@php.net>                             |   |          Andrei Zmievski <andrei@php.net>                            |   |          Stig Venaas <venaas@php.net>                                |   |          Jason Greene <jason@php.net>                                |   +----------------------------------------------------------------------+*//* $Id: array.c,v 1.199.2.44.2.16 2007/03/16 20:08:25 stas Exp $ */#include "php.h"#include "php_ini.h"#include <stdarg.h>#include <stdlib.h>#include <math.h>#include <time.h>#include <stdio.h>#if HAVE_STRING_H#include <string.h>#else#include <strings.h>#endif#ifdef PHP_WIN32#include "win32/unistd.h"#endif#include "zend_globals.h"#include "php_globals.h"#include "php_array.h"#include "basic_functions.h"#include "php_string.h"#include "php_rand.h"#include "php_smart_str.h"#ifdef ZTSint array_globals_id;#elsephp_array_globals array_globals;#endif#define EXTR_OVERWRITE			0#define EXTR_SKIP				1#define EXTR_PREFIX_SAME		2#define	EXTR_PREFIX_ALL			3#define	EXTR_PREFIX_INVALID		4#define	EXTR_PREFIX_IF_EXISTS	5#define	EXTR_IF_EXISTS			6#define EXTR_REFS				0x100#define SORT_REGULAR			0#define SORT_NUMERIC			1#define	SORT_STRING				2#define	SORT_LOCALE_STRING      5#define SORT_DESC				3#define SORT_ASC				4#define CASE_LOWER				0#define CASE_UPPER				1#define COUNT_NORMAL			0#define COUNT_RECURSIVE			1#define DIFF_NORMAL			0#define DIFF_ASSOC			1#define INTERSECT_NORMAL		0#define INTERSECT_ASSOC			1PHP_MINIT_FUNCTION(array){#ifdef ZTS	ts_allocate_id(&array_globals_id, sizeof(php_array_globals), NULL, NULL);#endif	REGISTER_LONG_CONSTANT("EXTR_OVERWRITE", EXTR_OVERWRITE, CONST_CS | CONST_PERSISTENT);	REGISTER_LONG_CONSTANT("EXTR_SKIP", EXTR_SKIP, CONST_CS | CONST_PERSISTENT);	REGISTER_LONG_CONSTANT("EXTR_PREFIX_SAME", EXTR_PREFIX_SAME, CONST_CS | CONST_PERSISTENT);	REGISTER_LONG_CONSTANT("EXTR_PREFIX_ALL", EXTR_PREFIX_ALL, CONST_CS | CONST_PERSISTENT);	REGISTER_LONG_CONSTANT("EXTR_PREFIX_INVALID", EXTR_PREFIX_INVALID, CONST_CS | CONST_PERSISTENT);	REGISTER_LONG_CONSTANT("EXTR_PREFIX_IF_EXISTS", EXTR_PREFIX_IF_EXISTS, CONST_CS | CONST_PERSISTENT);	REGISTER_LONG_CONSTANT("EXTR_IF_EXISTS", EXTR_IF_EXISTS, CONST_CS | CONST_PERSISTENT);	REGISTER_LONG_CONSTANT("EXTR_REFS", EXTR_REFS, CONST_CS | CONST_PERSISTENT);		REGISTER_LONG_CONSTANT("SORT_ASC", SORT_ASC, CONST_CS | CONST_PERSISTENT);	REGISTER_LONG_CONSTANT("SORT_DESC", SORT_DESC, CONST_CS | CONST_PERSISTENT);	REGISTER_LONG_CONSTANT("SORT_REGULAR", SORT_REGULAR, CONST_CS | CONST_PERSISTENT);	REGISTER_LONG_CONSTANT("SORT_NUMERIC", SORT_NUMERIC, CONST_CS | CONST_PERSISTENT);	REGISTER_LONG_CONSTANT("SORT_STRING", SORT_STRING, CONST_CS | CONST_PERSISTENT);	REGISTER_LONG_CONSTANT("SORT_LOCALE_STRING", SORT_LOCALE_STRING, CONST_CS | CONST_PERSISTENT);	REGISTER_LONG_CONSTANT("CASE_LOWER", CASE_LOWER, CONST_CS | CONST_PERSISTENT);	REGISTER_LONG_CONSTANT("CASE_UPPER", CASE_UPPER, CONST_CS | CONST_PERSISTENT);	REGISTER_LONG_CONSTANT("COUNT_NORMAL", COUNT_NORMAL, CONST_CS | CONST_PERSISTENT);	REGISTER_LONG_CONSTANT("COUNT_RECURSIVE", COUNT_RECURSIVE, CONST_CS | CONST_PERSISTENT);		return SUCCESS;}PHP_MSHUTDOWN_FUNCTION(array){#ifdef ZTS	ts_free_id(array_globals_id);#endif	return SUCCESS;}static void set_compare_func(int sort_type TSRMLS_DC){	switch (sort_type) {		case SORT_NUMERIC:			ARRAYG(compare_func) = numeric_compare_function;			break;		case SORT_STRING:			ARRAYG(compare_func) = string_compare_function;			break;#if HAVE_STRCOLL		case SORT_LOCALE_STRING:			ARRAYG(compare_func) = string_locale_compare_function;			break;#endif		case SORT_REGULAR:		default:			ARRAYG(compare_func) = compare_function;			break;	}}static int array_key_compare(const void *a, const void *b TSRMLS_DC){	Bucket *f;	Bucket *s;	zval result;	zval first;	zval second; 	f = *((Bucket **) a);	s = *((Bucket **) b);	if (f->nKeyLength == 0) {		Z_TYPE(first) = IS_LONG;		Z_LVAL(first) = f->h;	} else {		Z_TYPE(first) = IS_STRING;		Z_STRVAL(first) = f->arKey;		Z_STRLEN(first) = f->nKeyLength-1;	}	if (s->nKeyLength == 0) {		Z_TYPE(second) = IS_LONG;		Z_LVAL(second) = s->h;	} else {		Z_TYPE(second) = IS_STRING;		Z_STRVAL(second) = s->arKey;		Z_STRLEN(second) = s->nKeyLength-1;	} 	if (ARRAYG(compare_func)(&result, &first, &second TSRMLS_CC) == FAILURE) {		return 0;	} 	if (Z_TYPE(result) == IS_DOUBLE) {		if (Z_DVAL(result) < 0) {			return -1;		} else if (Z_DVAL(result) > 0) {			return 1;		} else {			return 0;		}	}	convert_to_long(&result);	if (Z_LVAL(result) < 0) {		return -1;	} else if (Z_LVAL(result) > 0) {		return 1;	} 	return 0;}static int array_reverse_key_compare(const void *a, const void *b TSRMLS_DC){	return array_key_compare(a, b TSRMLS_CC) * -1;}/* {{{ proto bool krsort(array array_arg [, int sort_flags])   Sort an array by key value in reverse order */PHP_FUNCTION(krsort){	zval *array;	long sort_type = SORT_REGULAR;	HashTable *target_hash;	if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "a|l", &array, &sort_type) == FAILURE) {		RETURN_FALSE;	}		target_hash = HASH_OF(array);	set_compare_func(sort_type TSRMLS_CC);		if (zend_hash_sort(target_hash, zend_qsort, array_reverse_key_compare, 0 TSRMLS_CC) == FAILURE) {		RETURN_FALSE;	}	RETURN_TRUE;}/* }}} *//* {{{ proto bool ksort(array array_arg [, int sort_flags])   Sort an array by key */PHP_FUNCTION(ksort){	zval *array;	long sort_type = SORT_REGULAR;	HashTable *target_hash;	if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "a|l", &array, &sort_type) == FAILURE) {		RETURN_FALSE;	}	target_hash = HASH_OF(array);	set_compare_func(sort_type TSRMLS_CC);		if (zend_hash_sort(target_hash, zend_qsort, array_key_compare, 0 TSRMLS_CC) == FAILURE) {		RETURN_FALSE;	}	RETURN_TRUE;}/* }}} */static int php_count_recursive(zval *array, long mode TSRMLS_DC){	long cnt = 0;	zval **element;	if (Z_TYPE_P(array) == IS_ARRAY) {		cnt = zend_hash_num_elements(Z_ARRVAL_P(array));		if (mode == COUNT_RECURSIVE) {			HashPosition pos;			for (zend_hash_internal_pointer_reset_ex(Z_ARRVAL_P(array), &pos);				 zend_hash_get_current_data_ex(Z_ARRVAL_P(array), (void **) &element, &pos) == SUCCESS;				 zend_hash_move_forward_ex(Z_ARRVAL_P(array), &pos)) {				cnt += php_count_recursive(*element, COUNT_RECURSIVE TSRMLS_CC);			}		}	}	return cnt;}/* {{{ proto int count(mixed var [, int mode])   Count the number of elements in a variable (usually an array) */PHP_FUNCTION(count){	zval *array;	long mode = COUNT_NORMAL;		if (zend_parse_parameters (ZEND_NUM_ARGS() TSRMLS_CC, "z|l", &array, &mode) == FAILURE)		return;		switch (Z_TYPE_P(array)) {		case IS_NULL:			RETURN_LONG(0);			break;		case IS_ARRAY:			RETURN_LONG (php_count_recursive (array, mode TSRMLS_CC));			break;		default:			RETURN_LONG(1);			break;	}}/* }}} *//* Numbers are always smaller than strings int this function as it * anyway doesn't make much sense to compare two different data types. * This keeps it consistant and simple. * * This is not correct any more, depends on what compare_func is set to. */static int array_data_compare(const void *a, const void *b TSRMLS_DC){	Bucket *f;	Bucket *s;	pval result;	pval *first;	pval *second; 	f = *((Bucket **) a);	s = *((Bucket **) b); 	first = *((pval **) f->pData);	second = *((pval **) s->pData);	if (ARRAYG(compare_func)(&result, first, second TSRMLS_CC) == FAILURE) {		return 0;	} 	if (Z_TYPE(result) == IS_DOUBLE) {		if (Z_DVAL(result) < 0) {			return -1;		} else if (Z_DVAL(result) > 0) {			return 1;		} else {			return 0;		}	}	convert_to_long(&result);	if (Z_LVAL(result) < 0) {		return -1;	} else if (Z_LVAL(result) > 0) {		return 1;	} 	return 0;}static int array_reverse_data_compare(const void *a, const void *b TSRMLS_DC){	return array_data_compare(a, b TSRMLS_CC)*-1;}static int array_natural_general_compare(const void *a, const void *b, int fold_case){	Bucket *f, *s;	zval *fval, *sval;	zval first, second;	int result; 	f = *((Bucket **) a);	s = *((Bucket **) b); 	fval = *((pval **) f->pData);	sval = *((pval **) s->pData);	first = *fval;	second = *sval;	if (Z_TYPE_P(fval) != IS_STRING) {		zval_copy_ctor(&first);		convert_to_string(&first);	}	if (Z_TYPE_P(sval) != IS_STRING) {		zval_copy_ctor(&second);		convert_to_string(&second);	}	result = strnatcmp_ex(Z_STRVAL(first), Z_STRLEN(first),						  Z_STRVAL(second), Z_STRLEN(second), fold_case);	if (Z_TYPE_P(fval) != IS_STRING)		zval_dtor(&first);	if (Z_TYPE_P(sval) != IS_STRING)		zval_dtor(&second);		return result;}static int array_natural_compare(const void *a, const void *b TSRMLS_DC){	return array_natural_general_compare(a, b, 0);}static int array_natural_case_compare(const void *a, const void *b TSRMLS_DC){	return array_natural_general_compare(a, b, 1);}static void php_natsort(INTERNAL_FUNCTION_PARAMETERS, int fold_case){	zval **array;	HashTable *target_hash;	if (ZEND_NUM_ARGS() != 1 || zend_get_parameters_ex(1, &array) == FAILURE) {		WRONG_PARAM_COUNT;	}	target_hash = HASH_OF(*array);	if (!target_hash) {		php_error_docref(NULL TSRMLS_CC, E_WARNING, "The argument should be an array");		return;	}	if (fold_case) {		if (zend_hash_sort(target_hash, zend_qsort, array_natural_case_compare, 0 TSRMLS_CC) == FAILURE) {			return;		}	} else {		if (zend_hash_sort(target_hash, zend_qsort, array_natural_compare, 0 TSRMLS_CC) == FAILURE) {			return;		}	}	RETURN_TRUE;}/* {{{ proto void natsort(array array_arg)   Sort an array using natural sort */PHP_FUNCTION(natsort){	php_natsort(INTERNAL_FUNCTION_PARAM_PASSTHRU, 0);}/* }}} *//* {{{ proto void natcasesort(array array_arg)   Sort an array using case-insensitive natural sort */PHP_FUNCTION(natcasesort){	php_natsort(INTERNAL_FUNCTION_PARAM_PASSTHRU, 1);}/* }}} *//* {{{ proto bool asort(array array_arg [, int sort_flags])   Sort an array and maintain index association */PHP_FUNCTION(asort){	zval *array;	long sort_type = SORT_REGULAR;	HashTable *target_hash;	if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "a|l", &array, &sort_type) == FAILURE) {		RETURN_FALSE;	}		target_hash = HASH_OF(array);	set_compare_func(sort_type TSRMLS_CC);		if (zend_hash_sort(target_hash, zend_qsort, array_data_compare, 0 TSRMLS_CC) == FAILURE) {		RETURN_FALSE;	}	RETURN_TRUE;}/* }}} *//* {{{ proto bool arsort(array array_arg [, int sort_flags])   Sort an array in reverse order and maintain index association */PHP_FUNCTION(arsort){	zval *array;	long sort_type = SORT_REGULAR;	HashTable *target_hash;	if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "a|l", &array, &sort_type) == FAILURE) {		RETURN_FALSE;	}		target_hash = HASH_OF(array);	set_compare_func(sort_type TSRMLS_CC);		if (zend_hash_sort(target_hash, zend_qsort, array_reverse_data_compare, 0 TSRMLS_CC) == FAILURE) {		RETURN_FALSE;	}	RETURN_TRUE;}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -