C++/CLI Join Generic Method Syntax for MSDN

Here is a code snippet for MSDN where the example for C++/CLI under “Join Generic Method” is missing.
The code is slightly different to make more sense (to me) and still can be used in the same spirit.
I changed the List objects to array and added a key field to the classes rather than using the data as the key.
 
#include "stdafx.h"
using namespace System;
using namespace System::Collections::Generic;
using namespace System::Linq; // ref: System.Core
 
public ref class Owner
{
public:
    property String^ Name;
    property String^ Id;
    property DateTime^ FirstVisit;
 
    Owner(String^ Name, String^ Id, DateTime^ FirstVisit)
    {
        this->Name = Name;
        this->Id = Id;
        this->FirstVisit = FirstVisit;
    }
};
 
public ref class Pet
{
public:
    property String^ Name;
    property String^ OwnerId;
 
    Pet(String^ Name, String^ OwnerId)
    {
        this->Name = Name;
        this->OwnerId = OwnerId;
    }
};
 
public ref class OwnerToPet
{
private:
    static String^ _getOwnerKey(Owner^ owner) { return owner->Id; }
    static String^ _getPetKey(Pet^ pet) { return pet->OwnerId; }
    static OwnerToPet^ _getOwnerToPet(Owner^ owner, Pet^ pet)
        { return gcnew OwnerToPet(owner->Name, pet->Name); }
 
public:
    property String^ OwnerName;
    property String^ PetName;
 
    OwnerToPet(String^ OwnerName, String^ PetName)
    {
        this->OwnerName = OwnerName;
        this->PetName = PetName;
    }
 
    static Func<Owner^, String^>^ getOwnerKey = gcnew Func<Owner^, String^>(_getOwnerKey);
    static Func<Pet^, String^>^ getPetKey = gcnew Func<Pet^, String^>(_getPetKey);
    static Func<Owner^, Pet^, OwnerToPet^>^ getOwnerToPet = gcnew Func<Owner^, Pet^, OwnerToPet^>(_getOwnerToPet);
};
 
static void JoinEx1()
{
    array<Owner^, 1>^ owners = 
    {
        { gcnew Owner("Hedlund, Magnus", "MH1", Convert::ToDateTime("05/20/1988")) },
        { gcnew Owner("Adams, Terry", "TA1", Convert::ToDateTime("11/23/1997")) },
        { gcnew Owner("Weiss, Charlotte", "CW1", Convert::ToDateTime("02/05/2001")) }
    };
 
    array<Pet^, 1>^ pets =
    {
        { gcnew Pet("Barley", "TA1") },
        { gcnew Pet("Boots", "TA1") },
        { gcnew Pet("Whiskers", "CW1") },
        { gcnew Pet("Daisy", "MH1") }
    };
 
    auto ownersAndPets =    Enumerable::Join <Owner^, Pet^, String^, OwnerToPet^>
    (
        owners,
        pets,
        OwnerToPet::getOwnerKey,
        OwnerToPet::getPetKey,
        OwnerToPet::getOwnerToPet
    );
 
    for each (OwnerToPet^ ownerAndPets in ownersAndPets)
    {
        Console::WriteLine("{0} - {1}", ownerAndPets->OwnerName, ownerAndPets->PetName);
    }
 
    /*
    This code produces the following output:
    Hedlund, Magnus - Daisy
    Adams, Terry - Barley
    Adams, Terry - Boots
    Weiss, Charlotte - Whiskers
    */
}