2011-10-25 73 views
0

我想用PHP解析用戶輸入的字符串日期。我需要刪除比這兩個上可接受的類之外的所有字符:PHP:將_not_中的所有單詞替換爲數組

1) [0-9,\./-] (numerals, comma, period, slash, and dash) 
2) An array of acceptable words: 
    $monthNames=array(
     "january"=>1, 
     "jan"=>1, 
     "february"=>2, 
     "feb"=>2 
    ); 

我試圖爆炸()荷蘭國際集團上字符字bounaries,然後除去各部分不是在陣列中,但導致相當混亂。有沒有一個完美的方式來完成這個?

謝謝!

+0

你應該表現出你的代碼,以便它更清楚你的目標是什麼。 – hakre

+0

您是否使用內置in_array()函數的php? http://php.net/manual/en/function.in-array.php – ford

+1

'strtotime()'http://php.net/manual/en/function.strtotime.php – Petah

回答

1

你可以使用strtotime()

echo strtotime("now"), "\n"; 
echo strtotime("10 September 2000"), "\n"; 
echo strtotime("+1 day"), "\n"; 
echo strtotime("+1 week"), "\n"; 
echo strtotime("+1 week 2 days 4 hours 2 seconds"), "\n"; 
echo strtotime("next Thursday"), "\n"; 
echo strtotime("last Monday"), "\n"; 

要檢查是否存在故障:

$str = 'Not Good'; 

// previous to PHP 5.1.0 you would compare with -1, instead of false 
if (($timestamp = strtotime($str)) === false) { 
    echo "The string ($str) is bogus"; 
} else { 
    echo "$str == " . date('l dS \o\f F Y h:i:s A', $timestamp); 
} 

http://php.net/manual/en/function.strtotime.php

而且DateTime::createFromFormat()可能是有用的。

http://www.php.net/manual/en/datetime.createfromformat.php

0

避免這種情況的最佳方法是將日期條目設置爲僅包含有效選項的表單並丟棄其餘部分。

+0

這是數年來輸入的數據。這不是新數據。 – dotancohen

0

你可以使用一個regulare表達式匹配日期,這裏有一個非常簡單的,基本的一個:

preg_match('/((Jan|Feb|Dec|\d{1,2})[ .\/-]){2,2}\d{1,4}/i', $str, $matches); 
echo $matches[0]; 

你必須添加其他月份,雖然。

寢食難安進一步的想法:

  • 不允許個月< 1> 12
  • 禁止一月一月2011
  • 禁止陌生年
  • ...
  • 廢了,找到一個好的一個;)

我想要一個兩步法:

  1. 精華的東西,看起來日期
  2. 使用內置的時間函數,以檢查是否可以建立一個時間戳是有道理的,從它。如果不能,就把它扔掉。
0

如果它是安全的假設,你的$即monthNames陣列具有小於26個元素,那麼下面的作品(雖然這肯定是一個「黑客」 - 我會提供了另一種答案,如果我能想到的東西值得被稱爲「優雅」):

<?php 

$text = 'january 3 february 7 xyz'; 
print 'original string=[' . $text . "]\n"; 

$monthNames = array(
    'january' => 1, 
    'jan' => 1, 
    'february' => 2, 
    'feb' => 2 
    // ... presumably there are some more array elements here... 
); 

// Map each monthNames key to a capital letter: 
$i = 65; // ASCII code for 'A' 
$mmap = array(); 
foreach (array_keys($monthNames) as $m) { 
    $c = chr($i); 
    $mmap[$c] = $m; 
    $i += 1; 
} 

// Strip out capital letters first: 
$text1 = preg_replace('/[A-Z]+/', "", $text); 

// Replace each month name with its letter: 
$text2 = str_replace(array_keys($monthNames), array_keys($mmap), $text1); 

// Filter out everything that is not allowed: 
$text3 = preg_replace('/[^0-9,\.\-A-Z]/', "", $text2); 

// Restore the original month names: 
$text4 = str_replace(array_keys($mmap), array_keys($monthNames), $text3); 

print 'filtered string=[' . $text4 . "]\n"; 
?> 

注:

  1. 如果你有26個以上的字符串過濾器過濾,排除了你可以編寫代碼來利用相同的想法,但海事組織變得相當難以讓人類(或無論如何我都可以)理解這些代碼。
  2. 如果您決定確實確實需要它們,您當然可以調整preg_replace()模式來單獨留下空格。
+1

我不確定,如果這能夠完美地工作:如果輸入的字符串是「1月3日2月7日XYZ」,會發生什麼? –

+0

的確,您的示例演示了一條缺失的邏輯:所有大寫字母都應該在替換步驟之前剝離出來。 – Peter

+0

修改後的代碼 - 添加了剝離大寫字母的初始步驟。 – Peter