Method 1: avoiding “A has B and B has A”

The following R code shows how to create a random Secret Santa list by:
1. Randomising the original list of names.
2. Assigning sequentially the names in the randomised list (First has Second, Second has Third, ., and Last has First).

The first step guarantees that the list will not be biased by the person who created the original list of names,while the second step guarantees that no one will be assigned to himself/herself.

library(babynames)

# A list of names
(names = babynames$name[1:30])
##  [1] "Mary"      "Anna"      "Emma"      "Elizabeth" "Minnie"   
##  [6] "Margaret"  "Ida"       "Alice"     "Bertha"    "Sarah"    
## [11] "Annie"     "Clara"     "Ella"      "Florence"  "Cora"     
## [16] "Martha"    "Laura"     "Nellie"    "Grace"     "Carrie"   
## [21] "Maude"     "Mabel"     "Bessie"    "Jennie"    "Gertrude" 
## [26] "Julia"     "Hattie"    "Edith"     "Mattie"    "Rose"
# length of the list
n <- length(names)

# Randomise the list
randlist <- sample(names)

# Creating the Secret Santa list based on assigning the names sequentially on the randomised list

# The last element in the randomised list is assigned to the first element
ListSS <- matrix(0,ncol=2,nrow=n) # Initialise the list

# Assigning the names
for( i in 1:(n-1)) ListSS[i,] <- c(randlist[i],randlist[i+1])
ListSS[n,] <- c(randlist[n],randlist[1])
colnames(ListSS) <- c("Santa", "Has")

# Raw list
ListSS
##       Santa       Has        
##  [1,] "Ida"       "Mattie"   
##  [2,] "Mattie"    "Julia"    
##  [3,] "Julia"     "Clara"    
##  [4,] "Clara"     "Laura"    
##  [5,] "Laura"     "Jennie"   
##  [6,] "Jennie"    "Annie"    
##  [7,] "Annie"     "Ella"     
##  [8,] "Ella"      "Gertrude" 
##  [9,] "Gertrude"  "Martha"   
## [10,] "Martha"    "Cora"     
## [11,] "Cora"      "Anna"     
## [12,] "Anna"      "Maude"    
## [13,] "Maude"     "Nellie"   
## [14,] "Nellie"    "Edith"    
## [15,] "Edith"     "Margaret" 
## [16,] "Margaret"  "Minnie"   
## [17,] "Minnie"    "Florence" 
## [18,] "Florence"  "Sarah"    
## [19,] "Sarah"     "Mabel"    
## [20,] "Mabel"     "Elizabeth"
## [21,] "Elizabeth" "Emma"     
## [22,] "Emma"      "Bertha"   
## [23,] "Bertha"    "Mary"     
## [24,] "Mary"      "Grace"    
## [25,] "Grace"     "Alice"    
## [26,] "Alice"     "Bessie"   
## [27,] "Bessie"    "Hattie"   
## [28,] "Hattie"    "Rose"     
## [29,] "Rose"      "Carrie"   
## [30,] "Carrie"    "Ida"
# Presenting the list in a nicer format
library(knitr)
kable(ListSS)
Santa Has
Ida Mattie
Mattie Julia
Julia Clara
Clara Laura
Laura Jennie
Jennie Annie
Annie Ella
Ella Gertrude
Gertrude Martha
Martha Cora
Cora Anna
Anna Maude
Maude Nellie
Nellie Edith
Edith Margaret
Margaret Minnie
Minnie Florence
Florence Sarah
Sarah Mabel
Mabel Elizabeth
Elizabeth Emma
Emma Bertha
Bertha Mary
Mary Grace
Grace Alice
Alice Bessie
Bessie Hattie
Hattie Rose
Rose Carrie
Carrie Ida

Method 2: Urn-drawing style avoiding “A has A”

The following R code shows how to create a random Secret Santa list by sampling one person at a time from the remaining persons, as you would do with an urn.

library(babynames)

# A list of names
(names = babynames$name[1:30])
##  [1] "Mary"      "Anna"      "Emma"      "Elizabeth" "Minnie"   
##  [6] "Margaret"  "Ida"       "Alice"     "Bertha"    "Sarah"    
## [11] "Annie"     "Clara"     "Ella"      "Florence"  "Cora"     
## [16] "Martha"    "Laura"     "Nellie"    "Grace"     "Carrie"   
## [21] "Maude"     "Mabel"     "Bessie"    "Jennie"    "Gertrude" 
## [26] "Julia"     "Hattie"    "Edith"     "Mattie"    "Rose"
# length of the list
n <- length(names)

valid <-1
while(valid>0){

names2 <- vector()
names2[1] <- sample(names[-1],1)
for(i in 2:(n-1)){
  names2[i] <- sample(setdiff(names[-i],names2),1)
}

names2[n] <- setdiff(names,names2)

valid <- sum((names==names2)*1) # checking if someone drew himself

}

# Raw list
ListSS <- cbind(names,names2)
colnames(ListSS) <- c("Santa", "Has")

# Presenting the list in a nicer format
library(knitr)
kable(ListSS)
Santa Has
Mary Edith
Anna Laura
Emma Bessie
Elizabeth Annie
Minnie Clara
Margaret Ella
Ida Florence
Alice Bertha
Bertha Julia
Sarah Mattie
Annie Ida
Clara Mabel
Ella Hattie
Florence Margaret
Cora Minnie
Martha Alice
Laura Mary
Nellie Carrie
Grace Sarah
Carrie Jennie
Maude Emma
Mabel Cora
Bessie Rose
Jennie Martha
Gertrude Maude
Julia Gertrude
Hattie Grace
Edith Elizabeth
Mattie Nellie
Rose Anna