Jump to content

Comparing two lists of email addresses with PHP


ionicle
Go to solution Solved by ionicle,

Recommended Posts

Hey again, everybody.

 

Need help with the solution of yet another task related to php.

 

I have two lists of email addresses - List 1 and List 2, so to say. The entire contents of List 2 is a part of List 1.

 

I would like for PHP to compare both lists and erase all the email addresses out of List 2, that are contained in List 1, plus all the email addresses, located at every domain name, listed within List 2.

 

For instance:

 

List 1:

 

brym@yahoo.com

gargamel@yahoo.com

grungel@gmail.com

shushlek@hotmail.com

gushterlqk@aol.com

shuslica@web.de

 

 

List 2:

 

brym@yahoo.com

grungel@gmail.com

 

 

After processing's completed, List 1 should look like this:

 

List 1:

 

shushlek@hotmail.com

gushterlqk@aol.com

shuslica@web.de

 

How would I go about doing that?

Link to comment
Share on other sites

That looks pretty convenient! Thing is, I not only need the entire List 2 to be removed from List 1, but also have all email addresses from List 1, matching with all domain names from List 2, be removed from List 1. 

 

array_diff() wouldn't help with that, I guess.

Edited by ionicle
Link to comment
Share on other sites

Try this

<?php
    // LIST 1
    $list1 = array(
        "brym@yahoo.com",
        "gargamel@yahoo.com",
        "grungel@gmail.com",
        "shushlek@hotmail.com",
        "gushterlqk@aol.com",
        "shuslica@web.de"
    );
    // LIST 2
    $list2 = array(
        "brym@yahoo.com",
        "grungel@gmail.com"
    );
    
    function extractUnwantedDomains($list2) {
        $list2Domains = array();
        foreach($list2 as $email) {
            $atPosition = strripos($email, '@');
            $dotPosition = strripos($email, '.', $atPosition + 1);
            $list2Domains[] = substr($email, ($atPosition + 1), ($dotPosition - 1) - ($atPosition));
        }
        return($list2Domains);
    }
    
    
    
    function extractFinalList($list1, $list2) {
        $finalList = array();
        $difference = array_diff($list1, $list2);
        $unwantedDomains = extractUnwantedDomains($list2);
        foreach($difference as $email) {
            foreach($unwantedDomains as $domain) {
                if(preg_match("/{$domain}/", $email)) {
                    continue(2);
                }
            }
            $finalList[] = $email;
        }
        return($finalList);
    }
    
    $finalList = extractFinalList($list1, $list2);
    var_dump($finalList);
Edited by JIXO
Link to comment
Share on other sites

just satisfying your second condition of removing all entries with the same domains found in the second list will remove the specific emails in the first condition.

 

the quickest code would be to preprocess the arrays of addresses so that you have an array of arrays, where the main key is the domain name (shown in pseudo code form, not the actual array) -

 

$array1['yahoo.com'] = array(brym@yahoo.com,gargamel@yahoo.com)

$array1['gmail.com'] = array(grungel@gmail.com)

$array1['hotmail.com'] = array(shushlek@hotmail.com)

...

 

$array2 ....

 

then (untested), you should be able to use array_diff() and the main key values in the second list will remove all the corresponding domain entries in the first list.

Edited by mac_gyver
Link to comment
Share on other sites

using array_diff_key() -

 $list1 = array(
"brym@yahoo.com",
"gargamel@yahoo.com",
"grungel@gmail.com",
"shushlek@hotmail.com",
"gushterlqk@aol.com",
"shuslica@web.de"
);

$list2 = array(
"brym@yahoo.com",
"grungel@gmail.com"
);

$array1 = array();
foreach($list1 as $email){
    list($name,$domain) = explode('@',$email);
    if(!isset($array1[$domain])){$array1[$domain] = array();}
    $array1[$domain][] = $email;
}

$array2 = array();
foreach($list2 as $email){
    list($name,$domain) = explode('@',$email);
    if(!isset($array2[$domain])){$array2[$domain] = array();}
    $array2[$domain][] = $email;
}

$result = array_diff_key($array1,$array2);

$final = array();
foreach($result as $arr){ // there should be a way to do this without a loop...
    $final = array_merge($final,$arr);
}

echo '<pre>';
print_r($final);
Link to comment
Share on other sites

  • Solution

Turns out JIXO's code works. For some reason though, when I load up a large number of email addies in the arrays, it screws up and spits out a blank result. No clue why.

 

I got another reply on Stackoverflow:

 

 

 
<?php
 
function domain($email){
$x=explode('@',$email);
return $x[1];
}

$list1=array("brym@yahoo.com","gargamel@yahoo.com","grungel@gmail.com","shushlek@hotmail.com","gushterlqk@aol.com","shuslica@web.de");//first list
$list2=array("brym@yahoo.com","grungel@gmail.com");//second list
$black_domains=array();
foreach($list2 as $l2){
$black_domains[]=domain($l2);
}
$new_list1=array();
foreach($list1 as $l1){
$domain=domain($l1);
if(!in_array($domain,$black_domains)){
$new_list1[]=$l1;
};
}

print_r($new_list1); //this gives new list
 
?>
 

 

 

That one works like a charm, even with very large lists.

Link to comment
Share on other sites

This thread is more than a year old. Please don't revive it unless you have something important to add.

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Reply to this topic...

×   Pasted as rich text.   Restore formatting

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

×
×
  • Create New...

Important Information

We have placed cookies on your device to help make this website better. You can adjust your cookie settings, otherwise we'll assume you're okay to continue.