PHP में स्ट्रिंग को पूर्णांक में बदलने का सबसे तेज़ तरीका


251

PHP का उपयोग करके, स्ट्रिंग को इस तरह बदलने का सबसे तेज़ तरीका क्या है: "123"पूर्णांक में?

वह विशेष विधि सबसे तेज़ क्यों है? यदि यह अनपेक्षित इनपुट प्राप्त करता है, जैसे कि "hello"या एक सरणी?


12
अच्छी तरह से अगर यह चोट (पठनीयता) नहीं है, तो सबसे कुशल तरीके से चीजें क्यों नहीं की जाती हैं?
nickf

19
यदि यह गति को नुकसान नहीं पहुंचाता है, तो सबसे पठनीय तरीके से चीजें क्यों नहीं की जाती हैं?
एंडी लेस्टर

4
@ और, नीचे दिए गए बेंचमार्क परीक्षणों को देखें। के बीच का अंतर (int)और intval()400% से अधिक हो सकता है!
२२

6
सबसे तेज़ मामले क्योंकि उपयोगकर्ता अनुभव के लिए गति मायने रखती है। जब आपके पास बहुत सारे ऑपरेशन चल रहे हों, तो आप उन्हें FAST करना चाहते हैं!
दीक्षा

13
एक मरे हुए घोड़े को लात मारे बिना, मैं यह भी कहूंगा कि इस मामले में गति बनाम पठनीयता का सवाल अप्रासंगिक है, क्योंकि प्रश्न को अनुकूलन के तहत टैग किया गया था। अनुकूलन के तहत टैग किए गए प्रश्न में गति चाहने का कारण स्वयं व्याख्यात्मक है।
पूरी तरह सेNotLizards

जवाबों:


371

मैंने अभी एक त्वरित बेंचमार्किंग व्यायाम स्थापित किया है:

Function             time to run 1 million iterations
--------------------------------------------
(int) "123":                0.55029
intval("123"):              1.0115  (183%)

(int) "0":                  0.42461
intval("0"):                0.95683 (225%)

(int) int:                  0.1502
intval(int):                0.65716 (438%)

(int) array("a", "b"):      0.91264
intval(array("a", "b")):    1.47681 (162%)

(int) "hello":              0.42208
intval("hello"):            0.93678 (222%)

औसतन, कॉलिंग इंटवल () ढाई गुना धीमी है, और अंतर सबसे बड़ा है यदि आपका इनपुट पहले से ही पूर्णांक है।

मैं जानना चाहूंगा कि हालांकि क्यों


अद्यतन: मैंने परीक्षण फिर से चलाए हैं, इस बार जबरदस्ती के साथ (0 + $var)

| INPUT ($x)      |  (int) $x  |intval($x) |  0 + $x   |
|-----------------|------------|-----------|-----------|
| "123"           |   0.51541  |  0.96924  |  0.33828  |
| "0"             |   0.42723  |  0.97418  |  0.31353  |
| 123             |   0.15011  |  0.61690  |  0.15452  |
| array("a", "b") |   0.8893   |  1.45109  |  err!     |
| "hello"         |   0.42618  |  0.88803  |  0.1691   |
|-----------------|------------|-----------|-----------|

परिशिष्ट: मैं अभी थोड़ा अप्रत्याशित व्यवहार कर रहा हूँ जिसे आपको इन तरीकों में से किसी एक को चुनते समय पता होना चाहिए:

$x = "11";
(int) $x;      // int(11)
intval($x);    // int(11)
$x + 0;        // int(11)

$x = "0x11";
(int) $x;      // int(0)
intval($x);    // int(0)
$x + 0;        // int(17) !

$x = "011";
(int) $x;      // int(11)
intval($x);    // int(11)
$x + 0;        // int(11) (not 9)

PHP 5.3.1 का उपयोग करके परीक्षण किया गया


9
यह शायद इस तथ्य के साथ कुछ करने के लिए है कि इंटाल () एक फ़ंक्शन कॉल को आमंत्रित करता है, जबकि कलाकारों को सीधे दुभाषिया की अभिव्यक्ति कैलकुलेटर में संभाला जाता है। यह भी कारण हो सकता है कि एक सह-गर्भाशय और भी तेज है।
स्टेटिक्सन

10
Php के अल्पज्ञात unary plus ऑपरेटर का उपयोग करके आपके जबरदस्ती के उदाहरण को और सरल बनाया जा सकता है। $ x + 0 -> + $ x
Ozzy

@ ओजी यह कमाल है। पारितोषिक के लिए धन्यवाद! +"15" == 15
caiosm1005

1
@ जॉन के बाद से वह है कि पहले कोड में केवल दो मामलों का परीक्षण करती है, (int)और intval, और प्रत्येक जोड़ी में, पर एक% देता है intval, आधार मामला होना चाहिए (int)। लेकिन आपके पास एक अच्छी बात यह है कि यह स्पष्ट होता अगर वह इतना स्पष्ट रूप से कहता, खासकर जब से उसने बाद में एक तीसरा मामला जोड़ा!
टूलमेकरस्टेव

2
क्या नए PHP संस्करणों में इस परिणाम में कोई बदलाव है?
Artyom

34

मुझे व्यक्तिगत रूप से लगता है कि कास्टिंग सबसे सुंदर है।

$iSomeVar = (int) $sSomeOtherVar;

क्या a हेलो ’जैसी स्ट्रिंग भेजी जानी चाहिए, इसे पूर्णांक ० पर भेज दिया जाएगा। such22 वर्ष की आयु’ जैसे स्ट्रिंग के लिए, इसे पूर्णांक २२ पर डाला जाएगा। जो भी किसी संख्या में पार्स नहीं कर सकता, वह ० हो जाता है।

यदि आप वास्तव में गति की आवश्यकता है, मुझे लगता है कि यहाँ अन्य सुझाव यह मानने में सही हैं कि जबरदस्ती सबसे तेज है।


7
दिलचस्प बात यह है कि सरणियों को 1. प्राप्त करने के लिए डाला जाता है।
12

2
@nickf ऐसा नहीं है - इसे 0 पर भी डाला जा सकता है। यह एक पूर्णांक के लिए बूलियन (सच | गलत) मूल्य रखता है - 'झूठा' = 0, 'सत्य' = 1. एक सरणी गलत है यदि यह 100% खाली है, और यह सच है अगर इसमें कोई डेटा है, भले ही यह खाली हो। तार या पूर्ण मान। यदि आप एक पूर्ण सरणी को पूर्णांक में डालना चाहते हैं, तो यह 0. हो जाएगा (हां, मैं इस पुराने से अवगत हूं!)
सुपर बिल्ली

15

एक परीक्षण चलाएं।

   string coerce:          7.42296099663
   string cast:            8.05654597282
   string fail coerce:     7.14159703255
   string fail cast:       7.87444186211

यह एक परीक्षण था जो प्रत्येक परिदृश्य को 10,000,000 बार चलाता था। :-)

सह-गर्भाशय है 0 + "123"

कास्टिंग है (integer)"123"

मुझे लगता है कि Co-ercion थोड़ा तेज है। ओह, और कोशिश 0 + array('123')करना PHP में एक घातक त्रुटि है। आप चाहते हैं कि आपका कोड आपूर्ति किए गए मूल्य के प्रकार की जांच कर सके।

मेरा परीक्षण कोड नीचे है।


function test_string_coerce($s) {
    return 0 + $s;
}

function test_string_cast($s) {
    return (integer)$s;
}

$iter = 10000000;

print "-- running each text $iter times.\n";

// string co-erce
$string_coerce = new Timer;
$string_coerce->Start();

print "String Coerce test\n";
for( $i = 0; $i < $iter ; $i++ ) {
    test_string_coerce('123');
}

$string_coerce->Stop();

// string cast
$string_cast = new Timer;
$string_cast->Start();

print "String Cast test\n";
for( $i = 0; $i < $iter ; $i++ ) {
    test_string_cast('123');
}

$string_cast->Stop();

// string co-erce fail.
$string_coerce_fail = new Timer;
$string_coerce_fail->Start();

print "String Coerce fail test\n";
for( $i = 0; $i < $iter ; $i++ ) {
    test_string_coerce('hello');
}

$string_coerce_fail->Stop();

// string cast fail
$string_cast_fail = new Timer;
$string_cast_fail->Start();

print "String Cast fail test\n";
for( $i = 0; $i < $iter ; $i++ ) {
    test_string_cast('hello');
}

$string_cast_fail->Stop();

// -----------------
print "\n";
print "string coerce:          ".$string_coerce->Elapsed()."\n";
print "string cast:            ".$string_cast->Elapsed()."\n";
print "string fail coerce:     ".$string_coerce_fail->Elapsed()."\n";
print "string fail cast:       ".$string_cast_fail->Elapsed()."\n";


class Timer {
    var $ticking = null;
    var $started_at = false;
    var $elapsed = 0;

    function Timer() {
        $this->ticking = null;
    }

    function Start() {
        $this->ticking = true;
        $this->started_at = microtime(TRUE);
    }

    function Stop() {
        if( $this->ticking )
            $this->elapsed = microtime(TRUE) - $this->started_at;
        $this->ticking = false;
    }

    function Elapsed() {
        switch( $this->ticking ) {
            case true: return "Still Running";
            case false: return $this->elapsed;
            case null: return "Not Started";
        }
    }
}

मैंने settypeइस परीक्षण में जोड़ा और PHP 7 का उपयोग करके इसे चलाया। कास्ट थोड़ा सामने आया और सभी पर एक बड़ा प्रदर्शन सुधार हुआ: स्ट्रिंग कोअर्स: 1.9255340099335 स्ट्रिंग कास्ट: 1.5142338275909 स्ट्रिंग सेटलमेंट: 4.149780212326 स्ट्रिंग फेल कॉयर: 1.2346560955048 स्ट्रिंग फ़ेल कास्ट: 1.39677112525 सेतुबंध: ४.१४
११'१६ को ०४:०४

9

आप केवल FLOAT का उपयोग करके लंबे स्ट्रिंग को पूर्णांक में बदल सकते हैं

$float = (float)$num;

या यदि आप चाहते हैं कि पूर्णांक अस्थायी फ्लोट नहीं है तो साथ जाएं

$float = (int)$num;

पूर्व के लिए।

(int)   "1212.3"   = 1212 
(float) "1212.3"   = 1212.3

1
है ना? यदि आप एक इंट चाहते हैं, तो आप उपयोग क्यों नहीं करेंगे (int)? यह सच हो सकता है कि यदि स्ट्रिंग में एक पूर्णांक होता है, तो वह (float)मान लौटाएगा जो पूर्णांक की तरह बहुत काम करता है (भले ही इसका आंतरिक प्रकार संभवतः है float), लेकिन आप ऐसा क्यों करेंगे, यदि विनिर्देश पूर्णांक मान वापस करना है ? मान लीजिए कि आने वाली स्ट्रिंग "1.3" है? आपको पूर्णांक नहीं मिलेगा। इसके अलावा, भविष्य में किसी को भी कोड पढ़ने के लिए, आपको कहना चाहिए कि आपका क्या मतलब है। यदि आपका मतलब है "यह पूर्णांक होना चाहिए", तो कहें (int), नहीं (float)
टूलमेकरस्टेव

7
$int = settype("100", "integer"); //convert the numeric string to int

3
मेरा मानना ​​है कि कुछ संदर्भ या प्रमाण क्रम में हैं!
मेहरान

$ int वास्तव में यहां एक बूलियन होगा, यदि कथन काम करता है, लेकिन यह तब से नहीं होगा जब सेनेटाइप () के पहले पैरामीटर को संदर्भ द्वारा पारित किया जाता है और इसलिए एक var होना चाहिए।
कतार

7

पूर्णांक किसी भी स्ट्रिंग से बाहर निकालना

$ = 'tel.123-12-33' में;

preg_match_all('!\d+!', $in, $matches);
$out =  (int)implode('', $matches[0]);

// $ आउट = '1231233';


आप सबसे अच्छे से बेहतरीन हैं! मैंने json डेटा स्ट्रिंग से पूर्णांक में कुछ संस्करण बदलने के लिए घंटों बिताए हैं, केवल आपकी विधि ने मदद की है! धन्यवाद!
कामनीबुला

4

अधिक तदर्थ बेंचमार्क परिणाम:

$ time php -r 'for ($x = 0;$x < 999999999; $x++){$i = (integer) "-11";}'     

real    2m10.397s
user    2m10.220s
sys     0m0.025s

$ time php -r 'for ($x = 0;$x < 999999999; $x++){$i += "-11";}'              

real    2m1.724s
user    2m1.635s
sys     0m0.009s

$ time php -r 'for ($x = 0;$x < 999999999; $x++){$i = + "-11";}'             

real    1m21.000s
user    1m20.964s
sys     0m0.007s

प्रत्येक लूप में 10x परीक्षण किए जा रहे कथन को लिखना बेहतर होगा, ताकि लूप ओवरहेड पर समय का प्रभुत्व न हो। जैसे { $i = +"-11"; $i = +"-11"; $i= +"-11"; $i= +"-11"; ... }। इसका शाब्दिक रूप से "-11"सीधे शाब्दिक मूल्य का उपयोग करना जोखिम भरा है , जब तक कि आप निश्चित नहीं हैं कि भाषा संकलन के समय कुछ काम नहीं करेगी। संभवतः PHP जैसी गतिशील भाषा के लिए ठीक है, लेकिन अगर भविष्य में अन्य भाषाओं में सूत्रों का परीक्षण करूँ तो मैं भविष्य के संदर्भ का उल्लेख करता हूँ। $x = "-11"परीक्षण लूप से पहले एक चर सेट करना सुरक्षित करें , और फिर इसका उपयोग करें। ताकि भीतर का कोड हो $i =+$x
टूलमेकरस्टेव

4

एक बेंचमार्क दौड़ा, और यह एक वास्तविक पूर्णांक प्राप्त करने का सबसे तेज़ तरीका निकला (सभी उपलब्ध तरीकों का उपयोग करके) है

$foo = (int)+"12.345";

बस उपयोग कर रहे हैं

$foo = +"12.345";

एक फ्लोट देता है।


2
यह बस से तेज है (int)"12.345"? कितने प्रतिशत से तेज?
टूलमेकरस्टेव
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.