เหตุผลในการใช้ฟังก์ชัน set.seed


185

หลายครั้งที่ฉันเห็นset.seedฟังก์ชันใน R ก่อนเริ่มโปรแกรม ฉันรู้ว่ามันใช้สำหรับการสร้างตัวเลขแบบสุ่ม จำเป็นต้องตั้งค่านี้หรือไม่?


2
สิ่งนี้จะตอบได้: stattrek.com/statistics/random-number-generator.aspx
duffymo

คำตอบ:


264

ความต้องการคือความต้องการที่เป็นไปได้สำหรับผลลัพธ์ที่ทำซ้ำได้ซึ่งอาจมาจากการพยายามดีบักโปรแกรมของคุณหรือแน่นอนจากการพยายามทำซ้ำสิ่งที่ทำ:

ผลลัพธ์สองรายการนี้เราจะ "ไม่ทำซ้ำ" ตามที่ฉันขอบางสิ่ง "สุ่ม":

R> sample(LETTERS, 5)
[1] "K" "N" "R" "Z" "G"
R> sample(LETTERS, 5)
[1] "L" "P" "J" "E" "D"

อย่างไรก็ตามทั้งสองนี้เหมือนกันเพราะฉันตั้งค่าเมล็ด :

R> set.seed(42); sample(LETTERS, 5)
[1] "X" "Z" "G" "T" "O"
R> set.seed(42); sample(LETTERS, 5)
[1] "X" "Z" "G" "T" "O"
R> 

มีวรรณกรรมมากมายในทุกสิ่งที่; Wikipedia เป็นการเริ่มต้นที่ดี ในสาระสำคัญ RNG เหล่านี้เรียกว่า Pseudo Random Number Generators เพราะในความเป็นจริงแล้วเป็นอัลกอริธึมเต็ม : รับเมล็ดเดียวกันคุณจะได้รับลำดับเดียวกัน และนั่นคือคุณสมบัติและไม่ใช่ข้อผิดพลาด


5
ขอบคุณ Dirk สำหรับตัวอย่างที่ดีเช่นนี้ .. ฉันได้ล้างมันด้วย 99% แต่ยังคงมีคำถาม 1. ในคำตอบของคุณคุณได้ใช้ set.seed 42 เป็นอาร์กิวเมนต์ .. มีเหตุผลใดที่เกี่ยวข้องกับการเลือกค่านี้
Vignesh

43
สำหรับ RNG ปกติที่มีคุณภาพดีค่าไม่สำคัญ "42" เป็นการอ้างอิงถึงหนังสือที่มีชื่อเสียง คนอื่นใช้วันเกิดหรือ "123" หรือเพียงแค่ "1"
Dirk Eddelbuettel

7
char2seedฟังก์ชั่นในแพคเกจ TeachingDemos ช่วยให้คุณสามารถตั้งค่าเมล็ดพันธุ์ (หรือเลือกเมล็ดพันธุ์ที่จะผ่านเข้าไปในset.seed) ตามสายอักขระ ตัวอย่างเช่นคุณอาจให้นักเรียนใช้ชื่อเป็นเมล็ดแล้วนักเรียนแต่ละคนมีชุดข้อมูลที่ไม่ซ้ำกัน แต่ผู้สอนสามารถสร้างชุดข้อมูลเดียวกันสำหรับการให้คะแนน
เกร็กสโนว์

8
เป็นไปได้ที่จะรันรหัสเดิมอีกครั้งด้วยเมล็ดที่แตกต่างกันจนกว่าคุณจะได้ผลลัพธ์ที่ "ดีที่สุด" (ฉันได้ทำสิ่งนี้เป็นตัวอย่าง) เพื่อป้องกันข้อกล่าวหาในการทำสิ่งนี้มันเป็นการดีที่สุดที่จะเลือกเมล็ดพันธุ์ที่มีความหมายชัดเจนไม่ว่าจะเป็นเมล็ดพันธุ์เดียวกันหรือวันที่หรือฉันใช้char2seedและนามสกุลของผู้ตรวจสอบหลักในโครงการ
เกร็กสโนว์

5
@DirkEddelbuettel มูลค่าเมล็ดสามารถเรื่องด้วยเหตุผลที่ไม่คำนวณเพื่อนของฉันมีปัญหากับการเผยแพร่ผลการจำลองของเขาเพราะรหัสเริ่มต้นด้วยset.seed(666)และผู้ตรวจสอบไม่ชอบเมล็ดปีศาจในรหัส ...
ทิม

33

คุณต้องตั้งค่าเมล็ดทุกครั้งที่คุณต้องการได้รับผลการสุ่มที่ทำซ้ำได้

set.seed(1)
rnorm(4)
set.seed(1)
rnorm(4)

17

เพียงเพิ่มบางส่วนเพิ่มเติม Need for set seed: ในโลกวิชาการถ้าใครอ้างว่าอัลกอริทึมของเขาประสบความสำเร็จพูด 98.05% ประสิทธิภาพในการจำลองหนึ่งอื่น ๆ จำเป็นต้องสามารถทำซ้ำได้

?set.seed

จะผ่านไฟล์ช่วยเหลือของฟังก์ชั่นนี้สิ่งเหล่านี้คือข้อเท็จจริงที่น่าสนใจ:

(1) set.seed () ส่งคืนค่า NULL ที่มองไม่เห็น

(2) "เริ่มแรกไม่มีเมล็ดชุดใหม่จะถูกสร้างขึ้นจากเวลาปัจจุบันและรหัสกระบวนการเมื่อจำเป็นต้องใช้หนึ่งดังนั้นช่วงที่แตกต่างกันจะให้ผลการจำลองที่แตกต่างกันโดยค่าเริ่มต้นอย่างไรก็ตามเมล็ดอาจถูกเรียกคืนจาก เซสชั่นก่อนหน้าถ้าพื้นที่ทำงานที่บันทึกไว้ก่อนหน้าถูกกู้คืน "นี่คือเหตุผลที่คุณต้องการเรียกใช้ set.seed () ด้วยค่าจำนวนเต็มเดียวกันในครั้งถัดไปที่คุณต้องการลำดับสุ่มแบบเดียวกัน


7

การแก้ไขเมล็ดนั้นเป็นสิ่งจำเป็นเมื่อเราพยายามเพิ่มประสิทธิภาพของฟังก์ชั่นที่เกี่ยวข้องกับตัวเลขที่สร้างแบบสุ่ม (เช่นในการประมาณตามการจำลอง) ถ้าเราไม่แก้ไขเมล็ดการเปลี่ยนแปลงที่เกิดจากการสุ่มตัวเลขที่แตกต่างกันน่าจะทำให้อัลกอริทึมการปรับให้เหมาะสมล้มเหลว

สมมติว่าด้วยเหตุผลบางอย่างคุณต้องการประเมินค่าเบี่ยงเบนมาตรฐาน (sd) ของการแจกแจงปกติที่มีค่าเฉลี่ยศูนย์โดยการจำลองให้ตัวอย่าง สิ่งนี้สามารถทำได้โดยใช้การเพิ่มประสิทธิภาพเชิงตัวเลขรอบขั้นตอนต่างๆ

  1. (การตั้งค่าเมล็ด)
  2. กำหนดค่าสำหรับ sd ให้สร้างข้อมูลแบบกระจายตามปกติ
  3. ประเมินความเป็นไปได้ที่ข้อมูลของคุณจะได้รับการแจกแจงแบบจำลอง

ฟังก์ชั่นต่อไปนี้ทำสิ่งนี้โดยไม่มีขั้นตอนที่ 1 เมื่อรวมมันแล้ว:

# without fixing the seed
simllh <- function(sd, y, Ns){
  simdist <- density(rnorm(Ns, mean = 0, sd = sd))
  llh <- sapply(y, function(x){ simdist$y[which.min((x - simdist$x)^2)] })
  return(-sum(log(llh)))
}
# same function with fixed seed
simllh.fix.seed <- function(sd,y,Ns){
  set.seed(48)
  simdist <- density(rnorm(Ns,mean=0,sd=sd))
  llh <- sapply(y,function(x){simdist$y[which.min((x-simdist$x)^2)]})
  return(-sum(log(llh)))
}

เราสามารถตรวจสอบประสิทธิภาพสัมพัทธ์ของทั้งสองฟังก์ชันในการค้นหาค่าพารามิเตอร์ที่แท้จริงด้วยการศึกษา Monte Carlo สั้น ๆ :

N <- 20; sd <- 2 # features of simulated data
est1 <- rep(NA,1000); est2 <- rep(NA,1000) # initialize the estimate stores
for (i in 1:1000) {
  as.numeric(Sys.time())-> t; set.seed((t - floor(t)) * 1e8 -> seed) # set the seed to random seed
  y <- rnorm(N, sd = sd) # generate the data
  est1[i] <- optim(1, simllh, y = y, Ns = 1000, lower = 0.01)$par
  est2[i] <- optim(1, simllh.fix.seed, y = y, Ns = 1000, lower = 0.01)$par
}
hist(est1)
hist(est2)

การกระจายผลลัพธ์ของการประมาณพารามิเตอร์คือ:

ฮิสโตแกรมของการประมาณพารามิเตอร์โดยไม่ต้องแก้ไขค่าเมล็ด ฮิสโตแกรมของพารามิเตอร์ประเมินการแก้ไขเมล็ด

เมื่อเราแก้ไขค่า seed การค้นหาเชิงตัวเลขจะสิ้นสุดลงใกล้กับค่าพารามิเตอร์ที่แท้จริงที่ 2 บ่อยกว่า


6

โดยทั่วไป set.seed () ฟังก์ชั่นจะช่วยนำชุดตัวแปรสุ่มแบบเดียวกันมาใช้ใหม่ซึ่งเราอาจต้องการในอนาคตเพื่อประเมินงานเฉพาะอีกครั้งด้วย varibales แบบสุ่มเดียวกัน

เราเพียงแค่ต้องประกาศก่อนที่จะใช้ฟังก์ชั่นสร้างตัวเลขสุ่มใด ๆ


อธิบายคำตอบอย่างละเอียด
Spry Techies
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.