Genera un numero casuale compreso tra 1 e 10


95

Poiché il mio approccio per una query di prova su cui ho lavorato in questa domanda non ha funzionato, sto provando qualcos'altro ora. C'è un modo per dire alla random()funzione di pg di ottenere solo numeri compresi tra 1 e 10?

Risposte:


152

Se per numeri compresi tra 1 e 10 intendi qualsiasi float che è> = 1 e <10, allora è facile:

select random() * 9 + 1

Questo può essere facilmente testato con:

# select min(i), max(i) from (
    select random() * 9 + 1 as i from generate_series(1,1000000)
) q;
       min       |       max
-----------------+------------------
 1.0000083274208 | 9.99999571684748
(1 row)

Se vuoi numeri interi, che sono> = 1 e <10, allora è semplice:

select trunc(random() * 9 + 1)

E ancora, semplice test:

# select min(i), max(i) from (
    select trunc(random() * 9 + 1) as i from generate_series(1,1000000)
) q;
 min | max
-----+-----
   1 |   9
(1 row)

seleziona la data (e.created_at) + (trunc (random () * 20)) dagli eventi e; risultato in: ERRORE: l'operatore non esiste: data + doppia precisione Trunc restituisce davvero numeri interi?
Bogdan Gusiev,

3
trunc()restituisce lo stesso tipo di dati dell'input (come indicato nel manuale). Devi trunc(random() * 20)::int
trasmettere

Mi chiedo se almeno in teoria sia possibile che random()restituisca un valore <1 che moltiplicato per 9 sarebbe> = 9 a causa della natura inesatta del tipo a doppia precisione ? In pratica, anche se fosse possibile, sarebbe assolutamente improbabile, ovviamente, a causa della precisione di circa 15 cifre.

1
Sto giocando con width_bucket(random(), 0, 1, 10)come alternativa

Sembra che le mie paure fossero infondate anche se confesso di non capire affatto la matematica :-)

17

Per riassumere e un po 'semplificare, puoi usare:

-- 0 - 9
select floor(random() * 10);
-- 0 - 10
SELECT floor(random() * (10 + 1));
-- 1 - 10
SELECT ceil(random() * 10);

E puoi testarlo come menzionato da @ user80168

-- 0 - 9
SELECT min(i), max(i) FROM (SELECT floor(random() * 10) AS i FROM generate_series(0, 100000)) q;
-- 0 - 10
SELECT min(i), max(i) FROM (SELECT floor(random() * (10 + 1)) AS i FROM generate_series(0, 100000)) q;
-- 1 - 10
SELECT min(i), max(i) FROM (SELECT ceil(random() * 10) AS i FROM generate_series(0, 100000)) q;

2
I documenti dicono "valore casuale nell'intervallo 0,0 <= x <1,0", quindi c'è almeno una possibilità teorica di ceil(random() * 10)restituire 0 - mi atterrei a floor.

1
Sono d'accordo con @JackDouglas, quindi per l'intervallo 1-10 dovrebbe essereSELECT floor(random() * 10 + 1);
SergiyKolesnikov

9

Se stai usando SQL Server, il modo corretto per ottenere il numero intero è

SELECT Cast(RAND()*(b-a)+a as int);

Dove

  • "b" è il limite superiore
  • "a" è il limite inferiore

Fai attenzione qui, se metti il ​​tuo limite inferiore come 1 e superiore come 10, otterrai solo i numeri 1-> 9. Altre risposte sembrano presumere che Tra 1 e 10 significhi 1-> 9 ... Suggerirei se 'tra' esclude il limite superiore dovrebbe escludere anche quello inferiore (cioè 2-> 9). SELEZIONA Cast (RAND () * ((b + 1) -a) + a come int);
Morvael

La domanda è chiaramente etichettata come domanda PostgreSQL.
Sebastian Palma

4

(trunc (random () * 10)% 10) + 1


ERRORE: l'operatore non esiste: doppia precisione% intero

1
E perché dovresti usare comunque il modulo? Questa logica non ha senso. Se ottieni "wrapping" non avrai la stessa distribuzione, e se non ne ottieni, non ne avrai bisogno.
ErikE

1

La versione corretta della risposta di hythlodayr.

-- ERROR:  operator does not exist: double precision % integer
-- LINE 1: select (trunc(random() * 10) % 10) + 1

L'output da truncdeve essere convertito in INTEGER. Ma si può fare a meno trunc. Quindi risulta essere semplice.

select (random() * 9)::INTEGER + 1

Genera un'uscita INTEGER nell'intervallo [1, 10] cioè sia 1 che 10 inclusi.

Per qualsiasi numero (float), vedere la risposta di user80168. cioè non convertirlo in INTEGER.


0

In realtà non so che tu voglia questo.

prova questo

INSERT INTO my_table (my_column)
SELECT
    (random() * 10) + 1
;

0

Questa procedura memorizzata inserisce un numero rand in una tabella. Attenzione, inserisce numeri infiniti. Smetti di eseguirlo quando ottieni abbastanza numeri.

crea una tabella per il cursore:

CREATE TABLE [dbo].[SearchIndex](
[ID] [int] IDENTITY(1,1) NOT NULL,
[Cursor] [nvarchar](255) NULL) 

PARTIRE

Crea una tabella per contenere i tuoi numeri:

CREATE TABLE [dbo].[ID](
[IDN] [int] IDENTITY(1,1) NOT NULL,
[ID] [int] NULL)

INSERIMENTO DELLO SCRIPT:

INSERT INTO [SearchIndex]([Cursor])  SELECT N'INSERT INTO ID  SELECT   FLOOR(rand() * 9 + 1)  SELECT COUNT (ID) FROM ID

CREAZIONE ED ESECUZIONE DELLA PROCEDURA:

CREATE PROCEDURE [dbo].[RandNumbers] AS
BEGIN
Declare  CURSE  CURSOR  FOR (SELECT  [Cursor] FROM [dbo].[SearchIndex]  WHERE [Cursor] IS NOT NULL)
DECLARE @RandNoSscript NVARCHAR (250)
OPEN CURSE
FETCH NEXT FROM CURSE
INTO @RandNoSscript 
WHILE @@FETCH_STATUS IS NOT NULL 
BEGIN
Print @RandNoSscript
EXEC SP_EXECUTESQL @RandNoSscript;  
 END
 END
GO

Riempi la tua tavola:

EXEC RandNumbers

3
La domanda riguarda Postgres, non SQL Server
a_horse_with_no_name
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.