Specify a computed column in SQL Server 2012 as an average - sql

Can I specify a computed column in SQL Server that averages another column?
So for example
CREATE TABLE dbo.Sales
(
TimeOfSale dateTime,
AmountOfSale money,
TotalSalesForMonth AS ?(Sum(AmountOfSale) over TimeofSale by month),
AverageForMonth AS ?(Sum(AmountOfSale) over TimeofSale by month / # sales per month)
);
I'm sure I could do this as a stored procedure and make another table, but I'm just curious as to whether it is possible to do so with computed columns.

Yes, you can do this, but you would have to write a UDF that calculates the aggregations and call the UDF in the Computed column definition.
Be advised that while this can be done, it may not be the best idea: https://blogs.msdn.microsoft.com/sqlcat/2011/11/28/a-computed-column-defined-with-a-user-defined-function-might-impact-query-performance/

Related

Add a derived attribute to existing table in SQL Developer

Is there any way to add a derived date/time column (to an existing table) to hold calculated running time from a race.
The values are in hours, round to 2 decimals. There are 2 columns for start time and end time in the table. Below is the last I've tried got a missing expression error.
ALTER TABLE race
ADD race_time AS (SELECT ROUND(DATEDIFF (endtime, starttime),2)FROM race);
There is no datediff() function in Oracle and you also don't need a SELECT statement to create a computed column:
ALTER TABLE race
ADD race_time AS (endtime - starttime);
If endtime and starttime are defined as timestamp the race_time column will be of the type interval.
If those two columns are date columns, the result will be a number representing the number of days between the two days
It's been a while since I used this functionality but I think it would look more like:
ALTER TABLE race
ADD race_time AS (ROUND(DATEDIFF (endtime, starttime),2))
Note that I'm not aware of a DATEDIFF function in Oracle - if you haven't written this yourself and are looking to get the number of hours between two dates it would be more like:
ALTER TABLE race
ADD race_time AS (ROUND((endtime - starttime)*24.0,2))
If your columns are timestamps, it would probably be easier to convert them to dates when doing the math
https://dbfiddle.uk/?rdbms=oracle_11.2&fiddle=3ac1f46f8d7296754d14a3de6191dbe8

How to create a custom primary key using strings and date

I have an order table in sql server and I need for the order number primary key to be like this
OR\20160202\01
OR is just a string
20160202 is the Date
01 is sequence number for that day
for second Order record the same day it would be
OR\20160202\02 and so on..
backlashes should also be included...
Whats the way to go about creating such a field in sql server (using version 2016)
EDIT: to add more context to what sequence number is, its just a way for this field composite or not to be unique. without a sequence number i would get duplicate records in DB because i could have many records the same day so date would remain the same thus it would be something like
OR\20160202 for all rows for that particular day so it would be duplicate. Adding a "sequence" number helps solve this.
The best way is to not create such a column in SQL. You're effectively combining multiple pieces of data into the same column, which shouldn't happen in a relational database for many reasons. A column should hold one piece of data.
Instead, create a composite primary key across all of the necessary columns.
composite pk
order varchar(20)
orDate DateTime
select *
, row_number() over (partition by cast(orDate as Date) order by orDate) as seq
from table
Will leave it to you on how to concatenate the data
That is presentation thing - don't make it a problem for the PK
About "sequence number for that day" (department, year, country, ...).
Almost every time I discussed such a requirement with end users it turned out to be just misunderstanding of how shared database works, a vague attempt to repeat old (separate databases, EXCEL files or even paper work) tricks on shared database.
So i second Tom H and others, first try not to do it.
If nevertheless you must do it, for legal or other unnegotiatable reasons then i hope you are on 2012+. Create SEQUENCE for every day.
Formatted PK is not a good idea.Composite key is a better approach.The combination of day as a date column and order number as a bigint column should be used.This helps in improving the query performance too.
You might want to explore 'Date Dimension' table. Date Dimension is commonly used table in data warehousing. It stores all the days of the calendar(based on your choice of years) and numeric generated keys for these days. Check this post on date dimension. It talks about creating one in SQL SERVER.
https://www.mssqltips.com/sqlservertip/4054/creating-a-date-dimension-or-calendar-table-in-sql-server/

Generate month and year from date and store automatically in table

Im working on sql server 2005, i have a column 'Date' of datatype datetime and want to extract month and year separately and store it in two separate columns in the same table as 'Date'. How do i do this and make it happen automatically everytime a new entry is entered where i dont have to manually input month and date.
You can use computed columns or trigger.
I recommend to use computed columns. It's very easy to implement and maintenance.
To get year and month use YEAR and MONTH functions
Computed Columns in SQL Server
DateTime functions in SQL Server

How to retrieve rows from database by passing month in where condition

How to retrieve rows from a SQL Server database by passing month in where condition, as I have used datetime datatype for the date column.
Is there any function is SQL Server, where I can send month and will get the row accordingly?
I would create an indexed computed column based on the month in the date column. This way queries will scale as you'll have a specific column indexed for querying against.
Using Month(yourdatecolumn) = somemonth is going to table scan (as in read every value to determine the month) at query execution time so wouldn't be a good idea for large volumes of data.
See this article for a commentary on why using functions in your where clause is bad.
SELECT * FROM table
WHERE MONTH(datecolumn) = 1
this will return all records for January

Storing time values in a database and getting the difference between two time fields

I am working on an application the stores time values in a database e.g Expected time of Arrival and actual time of arrival. What is the best way of storing these fields in a database?
What SQL query can I use to obtain the time difference between the two fields?
If you're on SQL Server 2008, use the TIME datatype. Declare those two fields
ExpectedTimeOfArrival TIME(7),
ActualTimeOfArrival TIME(7)
Read up on how to manipulate the TIME datatype here.
Once you have those two fields in place, you could add a computed column to your table that calculates the difference between those two, e.g. in minutes:
ALTER TABLE dbo.YourTable
ADD TimeDifference AS DATEDIFF(MINUTE, ActualTimeOfArrival, ExpectedTimeOfArrival)
and then you could query o that new column TimeDifference as if it were a normal, regular table column.