AskOverflow.Dev

AskOverflow.Dev Logo AskOverflow.Dev Logo

AskOverflow.Dev Navigation

  • Início
  • system&network
  • Ubuntu
  • Unix
  • DBA
  • Computer
  • Coding
  • LangChain

Mobile menu

Close
  • Início
  • system&network
    • Recentes
    • Highest score
    • tags
  • Ubuntu
    • Recentes
    • Highest score
    • tags
  • Unix
    • Recentes
    • tags
  • DBA
    • Recentes
    • tags
  • Computer
    • Recentes
    • tags
  • Coding
    • Recentes
    • tags
Início / dba / Perguntas / 123137
Accepted
AlwaysLearningNewStuff
AlwaysLearningNewStuff
Asked: 2015-12-08 12:46:05 +0800 CST2015-12-08 12:46:05 +0800 CST 2015-12-08 12:46:05 +0800 CST

solução padrão para armazenar unidades de medida

  • 772

INTRODUÇÃO E INFORMAÇÕES RELEVANTES:

Digamos que eu tenha uma tabela que armazene a altura e o peso de uma pessoa, mais ou menos assim:

PersonTable < # ID int, Name varchar(50), Height double, Weight double >

A altura é medida em centímetros e o peso em quilogramas.

PROBLEMA:

Meu problema é armazenar unidade de medida para altura e peso.

MEUS ESFORÇOS PARA RESOLVER ISSO:

  • Eu poderia tentar implementar o modelo EAV.
  • Eu poderia modificar a tabela adicionando colunas extras que contêm unidades de medida para Altura e Peso? Algo como abaixo:

    PersonTable < # ID int, 
                    Name varchar(50), 
                    Height double, $ HeightUnit_Id int, 
                    Weight double, $ WeightUnit_Id int >
    
    Units < #ID int, Desription varchar(20) >
    

  • HeightUnit_Id e WeightUnit_Id são chaves estrangeiras que fazem referência ao Id da tabela Units.

    PERGUNTA:

    Existe uma solução melhor do que as óbvias que mencionei acima, já que não gosto de ambas (o EAV pode ficar confuso se for mal feito e adicionar "colunas de unidade" extras parece um desperdício de espaço para mim)?

    database-design
    • 4 4 respostas
    • 10642 Views

    4 respostas

    • Voted
    1. Best Answer
      Solomon Rutzky
      2016-03-31T07:45:12+08:002016-03-31T07:45:12+08:00

      Assumindo que os tipos de medição não serão misturados (ou seja, nenhuma linha específica não irá misturar "kg" e "polegadas" OU "libras" e "cm"), e também assumindo que pelo menos parte da intenção desta Questão está relacionada a isso agora Pergunta relacionada excluída ( observe que o link a seguir não funcionará, a menos que você tenha pontos rep suficientes para ver os itens excluídos: Lidando com atributos compostos com parte constante ), então você só precisa indicar o sistema de medição usado por essa linha. Neste modelo, você teria uma única MeasurementSystemtabela com chave estrangeira para quaisquer tabelas contendo medições. Por exemplo (usando a sintaxe do Microsoft SQL Server):

      CREATE TABLE dbo.MeasurementSystem
      (
        MeasurementSystemID TINYINT NOT NULL
                            CONSTRAINT [PK_MeasurementSystem] PRIMARY KEY
                                       CLUSTERED,
        MeasurementSystemName NVARCHAR(50) NOT NULL
      );
      
      dbo.Person
      (
        PersonID            INT NOT NULL IDENTITY(1, 1)
                            CONSTRAINT [PK_Person] PRIMARY KEY
                                       CLUSTERED,
        MeasurementSystemID TINYINT NOT NULL
                            CONSTRAINT [FK_Person_MeasurementSystem]
                            FOREIGN KEY
                            REFERENCES dbo.MeasurementSystem (MeasurementSystemID),
        Name                NVARCHAR(50) NOT NULL
        Height              FLOAT,
        Weight              FLOAT,
        ...
      );
      
      INSERT INTO dbo.MeasurementSystem (MeasurementSystemID, MeasurementSystemName)
      VALUES (1, N'Metric');
      
      INSERT INTO dbo.MeasurementSystem (MeasurementSystemID, MeasurementSystemName)
      VALUES (2, N'United States customary units');
      

      Se você estiver misturando sistemas de medição e/ou se estiver permitindo várias unidades de medição, mesmo se confinado a um sistema (ou seja, permitindo "mm", "cm", "m"), será necessário haver um camada adicional para lidar com o aumento da granularidade, incluindo a necessidade de ter um campo FK para cada coluna de medida na Persontabela. (Posso adaptar o modelo acima para se adequar a isso, mas aguardarei alguns esclarecimentos antes de fazê-lo).


      Ou, se houver uma quantidade razoavelmente finita/limitada de combinações de várias unidades de peso e unidades de altura, você pode usar cada linha para representar uma das combinações aceitas (por exemplo, "cm & kg", "m & kg", "mm & kg" / "pol e lb", "pé e lb"). E então "US" vs "Metric" é apenas uma propriedade de cada linha da tabela de pesquisa. Por exemplo:

      CREATE TABLE dbo.MeasurementUnit
      (
        MeasurementUnitID     TINYINT NOT NULL
                                      CONSTRAINT [PK_MeasurementUnit] PRIMARY KEY
                                                 CLUSTERED,
        MeasurementSystem     CHAR(1) NOT NULL, -- "M" = Metric, "U" = US 
        MeasurementSystemName NVARCHAR(50) NOT NULL, -- "Metric" or "US Nonsense"
        HeightUnitsName       NVARCHAR(20) NOT NULL, -- "Centimeters"
        HeightUnitsAlias      NVARCHAR(5) NOT NULL, -- "cm"
        WeightUnitsName       NVARCHAR(20) NOT NULL, -- "Kilograms"
        WeightUnitsAlias      NVARCHAR(5) NOT NULL -- "kg"
      );
      
      dbo.Person
      (
        PersonID            INT NOT NULL IDENTITY(1, 1)
                            CONSTRAINT [PK_Person] PRIMARY KEY
                                       CLUSTERED,
        MeasurementUnitID   TINYINT NOT NULL
                                    CONSTRAINT [FK_Person_MeasurementUnit]
                                               FOREIGN KEY
                                              REFERENCES dbo.MeasurementUnit (MeasurementUnitID),
        Name                NVARCHAR(50) NOT NULL
        Height              FLOAT,
        Weight              FLOAT,
        ...
      );
      

      Ou, se houver necessidade de combinações de Unidades que cruzam diferentes sistemas de medição, eu usaria tabelas separadas -- uma para cada tipo de medição: "WeightUnits" e "HeightUnits". Eu não misturaria unidades para alturas e pesos na mesma tabela (ou seja, "kg" e "cm" em linhas diferentes). Por exemplo:

      CREATE TABLE dbo.WeightUnit
      (
        WeightUnitID      TINYINT NOT NULL
                                  CONSTRAINT [PK_WeightUnit] PRIMARY KEY
                                             CLUSTERED,
        MeasurementSystem CHAR(1) NOT NULL, -- "M" = Metric, "U" = US 
        WeightUnitName    NVARCHAR(50) NOT NULL, -- "Kilograms"
        WeightUnitAlias   NVARCHAR(5) NOT NULL -- "kg"
      );
      
      CREATE TABLE dbo.HeightUnit
      (
        HeightUnitID      TINYINT NOT NULL
                                  CONSTRAINT [PK_HeightUnit] PRIMARY KEY
                                             CLUSTERED,
        MeasurementSystem CHAR(1) NOT NULL, -- "M" = Metric, "U" = US 
        HeightUnitName    NVARCHAR(50) NOT NULL, -- "Centimeters"
        HeightUnitAlias   NVARCHAR(5) NOT NULL -- "cm"
      );
      

      Neste modelo, cada tipo de medição em qualquer tabela possui seu próprio FK pessoal para sua tabela de pesquisa de unidades de medição.

      • 6
    2. Joishi Bodio
      2015-12-08T13:12:16+08:002015-12-08T13:12:16+08:00

      Vendo como esta questão é em relação ao design, as respostas provavelmente serão bastante opinativas...

      Aqui está a minha opinião sobre como ele deve ser projetado. ;)

      Tabela para armazenar unidades de medida

      CREATE TABLE measure_unit (
        measure_unit_id, -- primary key
        name -- unique key .. values such as "inch" etc
      )
      

      Sua mesa pessoal...

      CREATE TABLE person (
        person_id, -- primary key
        name,
        measurement, -- example values would be 180
        measure_unit_id -- example values would be the pkey for centimeters
      )
      

      E então uma tabela de conversão

      CREATE TABLE measure_conversion (
        from_measure_unit_id, -- example would be pkey for centimeters
        to_measure_unit_id, -- example would be pkey for inches
        ratio -- example would be 0.393701 (centimeters * 0.393701 = inches)
        -- pkey is composite between both from and to values
      )
      

      Se uma unidade de medida não tiver uma entrada na tabela de conversão de medida para outro tipo específico de unidade, não haverá conversão direta disponível. (Por exemplo, cm -> polegadas funcionaria, mas cm -> horas não...) Deve ser fácil exibir suas medidas em diferentes unidades.

      Sua unidade de medida pode ser qualquer coisa que você quiser (distância/tempo/etc)... mas você pode querer adicionar um tipo de medida... não tenho certeza se me preocuparia com isso - depende do caso de uso.

      • 3
    3. jyao
      2016-03-31T10:07:33+08:002016-03-31T10:07:33+08:00

      Se suas unidades de medida de altura/peso forem realmente fixas , ou seja, altura=CMs, Peso=KGs, eu não introduziria nenhuma coluna adicional (ou lógica) para especificar a unidade de medida. Em vez disso, o que eu faria é apenas alterar o nome da coluna, como

      create table Person (ID int, Name varchar(50), Height_CM double, Weight_KG double)
      

      Dessa forma, posso remover qualquer confusão sobre a unidade de medida para as colunas Altura e Peso.

      • 3
    4. Dave
      2015-12-08T13:16:43+08:002015-12-08T13:16:43+08:00

      Depende do que você está projetando... um sistema OLTP normalizado teria uma tabela de medidas separada (ou algum nome semelhante) que fornece integridade referencial e otimizações de desempenho para cada unidade de medida possível.

      Se você estiver fazendo análises e lidar com unidades com pouca frequência e fizer menos conversões, isso pode ser armazenado como um atributo. Isso ainda seria raro - algo como respostas a pesquisas ou um padrão da indústria como metragem quadrada para imóveis. Mas o que mais é medido e faz sentido no mercado imobiliário? planos de chão? Agora temos polegadas... e quadrados e cúbicos. Voltamos a um design normalizado.

      Para altura, uma variedade de medidas são aplicáveis ​​e fazem todo o sentido em vários contextos. Provavelmente uma boa ideia usar um design como este:

      dbo.PersonHeight
      Height     MeasureFK
      62           2
      
      dbo.UnitsOfMeasure
      MeasureID  MeasureDescription
      2          Inches
      3          Centimeters
      

      Com esse design, você pode criar facilmente uma tabela de pesquisa/conversão agora:

      dbo.UnitConversions
      FromMeasureID    ToMeasureID    Conversion
      2                 3             0.39370079
      
      • 0

    relate perguntas

    • Os índices filtrados podem ajudar a melhorar as consultas baseadas em uma hora inserida ou isso deve ser evitado?

    • Qual é a diferença entre os tipos de dados MySQL VARCHAR e TEXT?

    • É melhor armazenar os valores calculados ou recalculá-los a pedido? [duplicado]

    • Armazenar vs calcular valores agregados

    • Quais são algumas maneiras de implementar um relacionamento muitos-para-muitos em um data warehouse?

    Sidebar

    Stats

    • Perguntas 205573
    • respostas 270741
    • best respostas 135370
    • utilizador 68524
    • Highest score
    • respostas
    • Marko Smith

      conectar ao servidor PostgreSQL: FATAL: nenhuma entrada pg_hba.conf para o host

      • 12 respostas
    • Marko Smith

      Como fazer a saída do sqlplus aparecer em uma linha?

      • 3 respostas
    • Marko Smith

      Selecione qual tem data máxima ou data mais recente

      • 3 respostas
    • Marko Smith

      Como faço para listar todos os esquemas no PostgreSQL?

      • 4 respostas
    • Marko Smith

      Listar todas as colunas de uma tabela especificada

      • 5 respostas
    • Marko Smith

      Como usar o sqlplus para se conectar a um banco de dados Oracle localizado em outro host sem modificar meu próprio tnsnames.ora

      • 4 respostas
    • Marko Smith

      Como você mysqldump tabela (s) específica (s)?

      • 4 respostas
    • Marko Smith

      Listar os privilégios do banco de dados usando o psql

      • 10 respostas
    • Marko Smith

      Como inserir valores em uma tabela de uma consulta de seleção no PostgreSQL?

      • 4 respostas
    • Marko Smith

      Como faço para listar todos os bancos de dados e tabelas usando o psql?

      • 7 respostas
    • Martin Hope
      Jin conectar ao servidor PostgreSQL: FATAL: nenhuma entrada pg_hba.conf para o host 2014-12-02 02:54:58 +0800 CST
    • Martin Hope
      Stéphane Como faço para listar todos os esquemas no PostgreSQL? 2013-04-16 11:19:16 +0800 CST
    • Martin Hope
      Mike Walsh Por que o log de transações continua crescendo ou fica sem espaço? 2012-12-05 18:11:22 +0800 CST
    • Martin Hope
      Stephane Rolland Listar todas as colunas de uma tabela especificada 2012-08-14 04:44:44 +0800 CST
    • Martin Hope
      haxney O MySQL pode realizar consultas razoavelmente em bilhões de linhas? 2012-07-03 11:36:13 +0800 CST
    • Martin Hope
      qazwsx Como posso monitorar o andamento de uma importação de um arquivo .sql grande? 2012-05-03 08:54:41 +0800 CST
    • Martin Hope
      markdorison Como você mysqldump tabela (s) específica (s)? 2011-12-17 12:39:37 +0800 CST
    • Martin Hope
      Jonas Como posso cronometrar consultas SQL usando psql? 2011-06-04 02:22:54 +0800 CST
    • Martin Hope
      Jonas Como inserir valores em uma tabela de uma consulta de seleção no PostgreSQL? 2011-05-28 00:33:05 +0800 CST
    • Martin Hope
      Jonas Como faço para listar todos os bancos de dados e tabelas usando o psql? 2011-02-18 00:45:49 +0800 CST

    Hot tag

    sql-server mysql postgresql sql-server-2014 sql-server-2016 oracle sql-server-2008 database-design query-performance sql-server-2017

    Explore

    • Início
    • Perguntas
      • Recentes
      • Highest score
    • tag
    • help

    Footer

    AskOverflow.Dev

    About Us

    • About Us
    • Contact Us

    Legal Stuff

    • Privacy Policy

    Language

    • Pt
    • Server
    • Unix

    © 2023 AskOverflow.DEV All Rights Reserve