生成随机出生日期

use*_*529 63 java random

我正在尝试使用Java程序为我的数据库中的人生成一个随机的出生日期.我该怎么做?

Sau*_*aul 74

import java.util.GregorianCalendar;

public class RandomDateOfBirth {

    public static void main(String[] args) {

        GregorianCalendar gc = new GregorianCalendar();

        int year = randBetween(1900, 2010);

        gc.set(gc.YEAR, year);

        int dayOfYear = randBetween(1, gc.getActualMaximum(gc.DAY_OF_YEAR));

        gc.set(gc.DAY_OF_YEAR, dayOfYear);

        System.out.println(gc.get(gc.YEAR) + "-" + (gc.get(gc.MONTH) + 1) + "-" + gc.get(gc.DAY_OF_MONTH));

    }

    public static int randBetween(int start, int end) {
        return start + (int)Math.round(Math.random() * (end - start));
    }
}
Run Code Online (Sandbox Code Playgroud)

  • 为了完整起见 - 你应该通过`Calendar`类(`Calendar.YEAR`,`Calendar.DAY_OF_YEAR`)而不是通过实例`gc`来使用访问常量. (5认同)
  • 这不是一个统一的分布,因为例如二月应该有更少的人. (3认同)
  • @lbalazscs - 的确如此.我更新了这个例子,现在应该好一点了. (2认同)

T.J*_*der 39

java.util.Date有一个构造函数,它接受自The Epoch以来的毫秒数,并且java.util.Random一个方法可以给你一个随机的毫秒数.您需要根据所需的DOB范围设置随机值的范围,但是应该这样做.

非常粗略:

Random  rnd;
Date    dt;
long    ms;

// Get a new random instance, seeded from the clock
rnd = new Random();

// Get an Epoch value roughly between 1940 and 2010
// -946771200000L = January 1, 1940
// Add up to 70 years to it (using modulus on the next long)
ms = -946771200000L + (Math.abs(rnd.nextLong()) % (70L * 365 * 24 * 60 * 60 * 1000));

// Construct a date
dt = new Date(ms);
Run Code Online (Sandbox Code Playgroud)


Jen*_*ann 35

基于Java 8的解决方案的代码段:

Random random = new Random();
int minDay = (int) LocalDate.of(1900, 1, 1).toEpochDay();
int maxDay = (int) LocalDate.of(2015, 1, 1).toEpochDay();
long randomDay = minDay + random.nextInt(maxDay - minDay);

LocalDate randomBirthDate = LocalDate.ofEpochDay(randomDay);

System.out.println(randomBirthDate);
Run Code Online (Sandbox Code Playgroud)

注意:这会生成1Jan1900(含)和1Jan2015(不包括)之间的随机日期.

:它基于纪元日,即相对于1Jan1970(EPOCH)的天数- EPOCH后的正面含义,EPOCH前的负面含义


您还可以创建一个小实用程序类:

public class RandomDate {
    private final LocalDate minDate;
    private final LocalDate maxDate;
    private final Random random;

    public RandomDate(LocalDate minDate, LocalDate maxDate) {
        this.minDate = minDate;
        this.maxDate = maxDate;
        this.random = new Random();
    }

    public LocalDate nextDate() {
        int minDay = (int) minDate.toEpochDay();
        int maxDay = (int) maxDate.toEpochDay();
        long randomDay = minDay + random.nextInt(maxDay - minDay);
        return LocalDate.ofEpochDay(randomDay);
    }

    @Override
    public String toString() {
        return "RandomDate{" +
                "maxDate=" + maxDate +
                ", minDate=" + minDate +
                '}';
    }
}
Run Code Online (Sandbox Code Playgroud)

并像这样使用它:

RandomDate rd = new RandomDate(LocalDate.of(1900, 1, 1), LocalDate.of(2010, 1, 1));
System.out.println(rd.nextDate());
System.out.println(rd.nextDate()); // birthdays ad infinitum
Run Code Online (Sandbox Code Playgroud)

  • 这是一个很好的答案,但是通过在构造函数中对min和max执行toEpochDay()转换并保存int结果而不是LocalDates,可以使实用程序类更有效.然后它只需要执行一次,而不是每次调用nextDate()一次. (4认同)

Rom*_*las 20

你需要定义一个随机日期,对吧?

一种简单的方法是Date使用long(自1970年1月1日以来的毫秒时间)生成一个新对象并减去随机long:

new Date(Math.abs(System.currentTimeMillis() - RandomUtils.nextLong()));
Run Code Online (Sandbox Code Playgroud)

(RandomUtils取自Apache Commons Lang).

当然,这远非一个真正的随机日期(例如你不会在1970年之前得到日期),但我认为它足以满足你的需求.

否则,您可以使用Calendar类创建自己的日期:

int year = // generate a year between 1900 and 2010;
int dayOfYear = // generate a number between 1 and 365 (or 366 if you need to handle leap year);
Calendar calendar = Calendar.getInstance();
calendar.set(Calendar.YEAR, randomYear);
calendar.set(Calendar.DAY_OF_YEAR, dayOfYear);
Date randomDoB = calendar.getTime();
Run Code Online (Sandbox Code Playgroud)

  • 使用标准随机是否真的很麻烦? (5认同)

Wit*_*rba 8

对于Java8->假设出生数据必须在当天之前:

import java.time.LocalDate;
import java.time.LocalTime;
import java.time.Period;
import java.time.temporal.ChronoUnit;
import java.util.Random;

public class RandomDate {

    public static LocalDate randomBirthday() {
        return LocalDate.now().minus(Period.ofDays((new Random().nextInt(365 * 70))));
    }

    public static void main(String[] args) {
        System.out.println("randomDate: " + randomBirthday());
    }
}
Run Code Online (Sandbox Code Playgroud)

  • 考虑使用 [`ThreadLocalRandom`](https://docs.oracle.com/javase/9​​/docs/api/java/util/concurrent/ThreadLocalRandom.html) 而不是实例化一个新的 [`Random`](https: //docs.oracle.com/javase/9​​/docs/api/java/util/Random.html) 每次。 (3认同)