Bài 1:

Imgur

select * from CITY where POPULATION > 100000 and COUNTRYCODE = "USA";

Bài 2:

Imgur

select NAME from CITY where POPULATION > 120000 and COUNTRYCODE = "USA";

Bài 3:

Imgur

select * from CITY; 

Bài 4:

Imgur

select * from CITY where ID = 1661;

Bài 5:

Imgur

SELECT * FROM CITY WHERE COUNTRYCODE = "JPN";

Bài 6:

Imgur

SELECT NAME FROM CITY WHERE COUNTRYCODE = "JPN";

Bài 7:

Imgur

SELECT CITY,STATE FROM STATION;

Bài 8:

Imgur

SELECT DISTINCT CITY FROM STATION WHERE ID%2=0;

Bài 9:

Imgur

Imgur

SELECT COUNT(CITY) - COUNT(DISTINCT CITY) FROM STATION;

** HARDER **

Bài 10:

Imgur

Imgur

SELECT CITY, LENGTH(CITY) FROM STATION
ORDER BY LENGTH(CITY),CITY
LIMIT 1;

SELECT CITY, LENGTH(CITY) FROM STATION
ORDER BY LENGTH(CITY) DESC,CITY
LIMIT 1;

Bài 11:

Imgur

SELECT DISTINCT CITY FROM STATION WHERE SUBSTRING(CITY,1,1) IN ('a','e','i','o','u','A','E','I','O','U'); 

Bài 12:

Imgur

SELECT DISTINCT CITY FROM STATION WHERE SUBSTRING(CITY,-1,1) IN ('a','e','i','o','u','A','E','I','O','U');

Bài 13:

Imgur

SELECT DISTINCT CITY FROM STATION WHERE SUBSTRING(CITY,1,1) IN ('a','e','i','o','u','A','E','I','O','U') AND SUBSTRING(CITY,-1,1) IN ('a','e','i','o','u','A','E','I','O','U');

Bài 14:

Imgur

SELECT DISTINCT CITY FROM STATION WHERE SUBSTRING(CITY,1,1) NOT IN ('a','e','i','o','u','A','E','I','O','U');

Bài 15:

Imgur

SELECT DISTINCT CITY FROM STATION WHERE SUBSTRING(CITY,-1,1) NOT IN ('a','e','i','o','u','A','E','I','O','U');

** HARDER LEVEL 2: **

Bài 16:

Imgur

SELECT DISTINCT CITY FROM STATION WHERE SUBSTRING(CITY,1,1) NOT IN ('a','e','i','o','u','A','E','I','O','U') OR SUBSTRING(CITY,-1,1) NOT IN ('a','e','i','o','u','A','E','I','O','U');

Bài 17:

Imgur

SELECT DISTINCT CITY FROM STATION WHERE SUBSTRING(CITY,1,1) NOT IN ('a','e','i','o','u','A','E','I','O','U') AND SUBSTRING(CITY,-1,1) NOT IN ('a','e','i','o','u','A','E','I','O','U');

Bài 18:

Imgur Imgur

SELECT NAME FROM STUDENTS WHERE MARKS > 75
ORDER BY RIGHT(NAME,3),ID;

Bài 19:

Imgur Imgur

SELECT NAME FROM EMPLOYEE
ORDER BY NAME;

Bài 20:

Imgur Imgur

SELECT NAME FROM EMPLOYEE WHERE SALARY > 2000 AND MONTHS < 10
ORDER BY EMPLOYEE_ID;

** HARDER LEVEL 3: **

Bài 21:

Imgur

SET @TEMP:=21; 
SELECT REPEAT('* ', @TEMP:= @TEMP - 1) 
FROM INFORMATION_SCHEMA.TABLES;

Bài 22:

Imgur

SET @TEMP:=0; 
SELECT REPEAT('* ', @TEMP:= @TEMP + 1) 
FROM INFORMATION_SCHEMA.TABLES
WHERE @TEMP < 20;

Bài 23:

Imgur Imgur

SELECT CASE
            WHEN A+B>C AND B+C>A AND A+C>B THEN
                CASE
                    WHEN A=B AND B=C THEN 'Equilateral'
                    WHEN A=B OR B=C OR A=C THEN 'Isosceles'
                    ELSE 'Scalene'
                END
            ELSE 'Not A Triangle'
            END
FROM TRIANGLES;

Bài 24:

Imgur Imgur Imgur

SELECT CONCAT(NAME,'(',LEFT(OCCUPATION,1),')') FROM OCCUPATIONS 
ORDER BY NAME;
SELECT CONCAT('There are a total of ',COUNT(OCCUPATION),' ',LOWER(OCCUPATION),'s.') AS TOTAL FROM OCCUPATIONS
GROUP BY OCCUPATION ORDER BY TOTAL;

*** Note ***

GROUP BY: Là sort lại và chỉ lấy cái đại diện thôi còn ORDER BY: thì cũng sắp xếp lại và lấy luôn những cái giống nhau !

(**) Bài 25:

Imgur Imgur Imgur

Solution: [Don’t see example because input not example]

** Step 1: **

Create a virtual table in your head of data given to us. It look like us:

Imgur

SELECT
    case when Occupation='Doctor' then Name end as Doctor,
    case when Occupation='Professor' then Name end as Professor,
    case when Occupation='Singer' then Name end as Singer,
    case when Occupation='Actor' then Name end as Actor
FROM OCCUPATIONS

Explanation: END AS in mysql

SELECT OrderID, Quantity,
CASE WHEN Quantity > 30 THEN 'The quantity is greater than 30'
WHEN Quantity = 30 THEN 'The quantity is 30'
ELSE 'The quantity is under 30'
END AS QuantityText
FROM OrderDetails;

Imgur

** Step 2: **

Create an index column with respect to occupation as “RowNumber”

Imgur

Notice from the image, under professor column, the first Name is indexed as 1, the next name “Birtney” as 2. That is what I mean by index w.r.t occupation.

The below code will only give the “RowNumber” column, to get the result like in image proceed to step 3

set @r1=0, @r2=0, @r3=0, @r4=0;

SELECT case 
	when Occupation='Doctor' then (@r1:=@r1+1)
        when Occupation='Professor' then (@r2:=@r2+1)
        when Occupation='Singer' then (@r3:=@r3+1)
        when Occupation='Actor' then (@r4:=@r4+1) end as RowNumber

FROM OCCUPATIONS

** Step 3: **

Combine the result from step 1 and step 2:

set @r1=0, @r2=0, @r3=0, @r4=0;

SELECT case 
	when Occupation='Doctor' then (@r1:=@r1+1)
        when Occupation='Professor' then (@r2:=@r2+1)
        when Occupation='Singer' then (@r3:=@r3+1)
        when Occupation='Actor' then (@r4:=@r4+1) end as RowNumber,
        case when Occupation='Doctor' then Name end as Doctor,
        case when Occupation='Professor' then Name end as Professor,
        case when Occupation='Singer' then Name end as Singer,
        case when Occupation='Actor' then Name end as Actor

FROM OCCUPATIONS

** Step 4: **

Now, Order_by name the Group_By RowNumber

Using Min/Max, if there is a name, it will return it, if not, return NULL.

set @r1=0, @r2=0, @r3=0, @r4=0;
select min(Doctor), min(Professor), min(Singer), min(Actor)
from(
  select case when Occupation='Doctor' then (@r1:=@r1+1)
            when Occupation='Professor' then (@r2:=@r2+1)
            when Occupation='Singer' then (@r3:=@r3+1)
            when Occupation='Actor' then (@r4:=@r4+1) end as RowNumber,
    case when Occupation='Doctor' then Name end as Doctor,
    case when Occupation='Professor' then Name end as Professor,
    case when Occupation='Singer' then Name end as Singer,
    case when Occupation='Actor' then Name end as Actor
  from OCCUPATIONS
  order by Name
	) temp
group by RowNumber;

Bài 25:

Imgur Imgur Imgur Imgur Imgur

select c.company_code, c.founder, 
    count(distinct l.lead_manager_code), count(distinct s.senior_manager_code), 
    count(distinct m.manager_code),count(distinct e.employee_code) 
from Company c, Lead_Manager l, Senior_Manager s, Manager m, Employee e 
where c.company_code = l.company_code 
    and l.lead_manager_code=s.lead_manager_code 
    and s.senior_manager_code=m.senior_manager_code 
    and m.manager_code=e.manager_code 
group by c.company_code, c.founder 
order by c.company_code;

Super Hard (Join)

Bài 26:

Imgur Imgur Imgur Imgur

SELECT h.hacker_id, h.name, t1.total_score
FROM( 
    SELECT hacker_id, SUM(max_score) AS total_score
    FROM(
        SELECT hacker_id, MAX(score) AS max_score
        FROM Submissions
        GROUP BY hacker_id, challenge_id
    ) t
    GROUP BY hacker_id
) t1
JOIN Hackers h 
ON h.hacker_id = t1.hacker_id 
WHERE t1.total_score <>0 
ORDER BY total_score DESC, hacker_id;

Bài 27:

Imgur

SELECT ROUND(LONG_W,4)
FROM STATION
WHERE LAT_N = (SELECT MIN(LAT_N) FROM STATION WHERE LAT_N >38.7780);

Bài 28:

Imgur

SELECT 
    ROUND(ABS(MAX(LAT_N)-MIN(LAT_N))+ABS(MAX(LONG_W)-MIN(LONG_W)),4)
FROM STATION;

Bài 29:

Imgur

select 
    round(sqrt(
        power((max(LAT_N)-min(LAT_N)),2) + 
        power((max(LONG_W)-min(LONG_W)),2)
    ),4)
from STATION;

Bài 30:

Imgur

Select round(S.LAT_N,4) from station AS S where (select count(Lat_N) from station where Lat_N < S.LAT_N ) = (select count(Lat_N) from station where Lat_N > S.LAT_N);
Note: AS là dùng để viết tắt tên bảng khi tên bảng dài quá, và dùng S.LAT_N là để đối tượng đang được nhắc tới !

Bài 31:

Imgur

SELECT ROUND(AVG(POPULATION),0) FROM CITY;

Bài 32:

Imgur

select sum(population) from city where countrycode = "JPN";

Bài 33:

Imgur

select abs(max(population)-min(population)) from city;

Bài 34:

Imgur

select count(population) from CITY where population > 100000;

Bài 35:

Imgur

select sum(population) from city where district = "California";

Bài 36:

Imgur

select avg(population) from city where district = "California";

Bài 37:

Imgur Imgur Imgur

select ceil(avg(salary)-avg(replace(salary,'0',''))) from employees;

Bài 38:

Imgur Imgur Imgur

salary*month --- first to calculate total earnings we multiply month * salary

count() -- next for counting no of employees having that salary we use count()

group by 1 -- ill take simple example..consider query SELECT name , id FROM employee group by 1; in this query there are 2 columns i.e., name and id...So we have to group it by 1st column that is name.

order by earning desc -- it will order the table in desc order do that max value appears frst.

limit 1 -- it will limit the table to 1 row only. so the query displays the frst row only.

Imgur

select (salary*months) as earnings , count(*) from employee group by 1 order by earnings
desc limit 1;

Bài 39:

Imgur Imgur

SELECT 
    ROUND(SUM(LAT_N), 2),
    ROUND(SUM(LONG_W), 2) 
FROM STATION;

Bài 40:

Imgur

SELECT ROUND(SUM(LAT_N),4) FROM STATION WHERE 38.7880< LAT_N AND LAT_N < 137.2345;

Bài 41:

Imgur

select round(max(LAT_N),4) from station where LAT_N < 137.2345;

Bài 42:

Imgur

select round(LONG_W,4) from STATION where LAT_N = (select MAX(LAT_N) from STATION where LAT_N<137.2345);

Bài 43:

Imgur

SELECT ROUND(LAT_N,4) FROM STATION WHERE LAT_N = (SELECT MIN(LAT_N) FROM STATION WHERE LAT_N>38.7780);

Bài 44:

Imgur Imgur Imgur Imgur Imgur

SELECT W.ID, P.AGE, W.COINS_NEEDED, W.POWER 
FROM WANDS AS W
JOIN WANDS_PROPERTY AS P
ON (W.CODE = P.CODE)
WHERE P.IS_EVIL = 0 AND W.COINS_NEEDED = (SELECT MIN(COINS_NEEDED)
                                         FROM WANDS AS X
                                         JOIN WANDS_PROPERTY AS Y
                                         ON (X.CODE = Y.CODE)
                                         WHERE X.POWER = W.POWER AND Y.AGE = P.AGE)
ORDER BY W.POWER DESC, P.AGE DESC;  

Bài 44:

Imgur

SELECT SUM(CITY.POPULATION) FROM CITY
INNER JOIN COUNTRY 
ON CITY.COUNTRYCODE = COUNTRY.CODE 
WHERE COUNTRY.CONTINENT = 'Asia';

Bài 45:

Imgur Imgur

SELECT CITY.NAME FROM CITY
INNER JOIN COUNTRY
ON CITY.COUNTRYCODE = COUNTRY.CODE 
WHERE COUNTRY.CONTINENT = 'Africa';

Bài 46:

Imgur Imgur

SELECT COUNTRY.CONTINENT, FLOOR(AVG(CITY.POPULATION))
FROM COUNTRY, CITY
WHERE COUNTRY.CODE = CITY.COUNTRYCODE 
GROUP BY COUNTRY.CONTINENT;

Bài 47:

Imgur Imgur Imgur

SELECT IF(GRADES.GRADE>=8,STUDENTS.NAME, NULL), GRADES.GRADE, STUDENTS.MARKS
FROM GRADES, STUDENTS 
WHERE STUDENTS.MARKS BETWEEN GRADES.MIN_MARK AND GRADES.MAX_MARK
ORDER BY GRADES.GRADE DESC, STUDENTS.NAME;

Bài 48:

Imgur Imgur Imgur Imgur Imgur

SELECT H.HACKER_ID, H.NAME
FROM HACKERS H
INNER JOIN SUBMISSIONS S
ON H.HACKER_ID = S.HACKER_ID
INNER JOIN CHALLENGES C
ON S.CHALLENGE_ID = C.CHALLENGE_ID
INNER JOIN DIFFICULTY D
ON C.DIFFICULTY_LEVEL = D.DIFFICULTY_LEVEL
WHERE S.SCORE = D.SCORE AND C.DIFFICULTY_LEVEL = D.DIFFICULTY_LEVEL
GROUP BY H.HACKER_ID, H.NAME
HAVING COUNT(S.HACKER_ID) > 1
ORDER BY COUNT(S.HACKER_ID) DESC, S.HACKER_ID ASC;

Bài 49:

Imgur Imgur Imgur Imgur Imgur Imgur

SELECT H.HACKER_ID, 
       H.NAME, 
       COUNT(C.CHALLENGE_ID) AS C_COUNT
FROM HACKERS H
JOIN CHALLENGES C ON C.HACKER_ID = H.HACKER_ID
GROUP BY H.HACKER_ID, H.NAME
HAVING C_COUNT = 
    (SELECT COUNT(C2.CHALLENGE_ID) AS C_MAX
     FROM CHALLENGES AS C2
     GROUP BY C2.HACKER_ID 
     ORDER BY C_MAX DESC LIMIT 1)
OR C_COUNT IN 
    (SELECT DISTINCT C_COMPARE AS C_UNIQUE
     FROM (SELECT H2.HACKER_ID, 
                  H2.NAME, 
                  COUNT(CHALLENGE_ID) AS C_COMPARE
           FROM HACKERS H2
           JOIN CHALLENGES C ON C.HACKER_ID = H2.HACKER_ID
           GROUP BY H2.HACKER_ID, H2.NAME) COUNTS
     GROUP BY C_COMPARE
     HAVING COUNT(C_COMPARE) = 1)
ORDER BY C_COUNT DESC, H.HACKER_ID;

Bài 50:

Imgur Imgur Imgur

-- solution 1
SET @project = 0;
SET @last_date = NULL;
SELECT MIN(start_date), MAX(end_date)
FROM (SELECT
            start_date, end_date,
            (CASE WHEN start_date = @last_date THEN @project
                  ELSE @project:=@project+1 END) AS project,
            @last_date:=end_date
            FROM (SELECT start_date, end_date FROM projects ORDER BY start_date) sorted) temp
GROUP BY project
ORDER BY COUNT(1), MIN(start_date);
-- Solution 2
SELECT start_date, MIN(end_date)
FROM (SELECT start_date FROM projects
      WHERE start_date NOT IN (SELECT end_date FROM projects)) a
      INNER JOIN
     (SELECT end_date FROM projects
      WHERE end_date NOT IN (SELECT start_date FROM projects)) b
WHERE start_date < end_date
GROUP BY start_date
ORDER BY MIN(end_date) - start_date, start_date;

Bài 51:

Imgur Imgur Imgur

SELECT S.NAME 
FROM STUDENTS S
JOIN FRIENDS F ON S.ID = F.ID 
JOIN PACKAGES P1 ON S.ID = P1.ID
JOIN PACKAGES P2 ON F.FRIEND_ID = P2.ID 
WHERE P2.SALARY > P1.SALARY 
ORDER BY P2.SALARY 

Bài 52:

Imgur Imgur

SELECT X, Y FROM FUNCTIONS F1
    WHERE EXISTS(SELECT * FROM FUNCTIONS F2 WHERE F2.Y = F1.X
    AND F2.X = F1.Y AND F2.X > F1.X) AND (X != Y)
UNION
SELECT X,Y FROM FUNCTIONS F1 WHERE X = Y AND 
    ((SELECT COUNT(*) FROM FUNCTIONS WHERE X = F1.X AND Y = F1.X) > 1)
      ORDER BY X;

(**) Bài 53:

Imgur Imgur Imgur Imgur

/*
Working Platform:- MySQL
*/
SELECT A.CONTEST_ID, A.HACKER_ID, A.NAME, 
        SUM(TOTAL_SUBMISSIONS) AS TOTAL_SUBMISSIONS, 
        SUM(TOTAL_ACCEPTED_SUBMISSIONS) AS TOTAL_ACCEPTED_SUBMISSIONS,
        SUM(TOTAL_VIEWS) AS TOTAL_VIEWS,
        SUM(TOTAL_UNIQUE_VIEWS) AS TOTAL_UNIQUE_VIEWS
FROM CONTESTS AS A
LEFT JOIN COLLEGES AS B
    ON A.CONTEST_ID = B.CONTEST_ID
LEFT JOIN CHALLENGES AS C
    ON B.COLLEGE_ID = C.COLLEGE_ID 
LEFT JOIN (SELECT CHALLENGE_ID, SUM(TOTAL_VIEWS) AS TOTAL_VIEWS, 
                  SUM(TOTAL_UNIQUE_VIEWS) AS TOTAL_UNIQUE_VIEWS
           FROM VIEW_STATS
           GROUP BY CHALLENGE_ID) AS D 
    ON C.CHALLENGE_ID = D.CHALLENGE_ID 
LEFT JOIN (SELECT CHALLENGE_ID, SUM(TOTAL_SUBMISSIONS) AS TOTAL_SUBMISSIONS, 
                  SUM(TOTAL_ACCEPTED_SUBMISSIONS) AS TOTAL_ACCEPTED_SUBMISSIONS
           FROM SUBMISSION_STATS
           GROUP BY CHALLENGE_ID) AS E
    ON C.CHALLENGE_ID = E.CHALLENGE_ID
GROUP BY A.CONTEST_ID, A.HACKER_ID, A.NAME
HAVING (TOTAL_SUBMISSIONS + TOTAL_ACCEPTED_SUBMISSIONS + TOTAL_VIEWS + TOTAL_UNIQUE_VIEWS) > 0 
ORDER BY A.CONTEST_ID;

(**) Bài 54:

Imgur Imgur Imgur Imgur

SELECT SUBMISSION_DATE,
(SELECT COUNT(DISTINCT HACKER_ID)  
 FROM SUBMISSIONS S2  
 WHERE S2.SUBMISSION_DATE = S1.SUBMISSION_DATE AND    
(SELECT COUNT(DISTINCT S3.SUBMISSION_DATE) 
 FROM SUBMISSIONS S3 WHERE S3.HACKER_ID = S2.HACKER_ID AND S3.SUBMISSION_DATE < S1.SUBMISSION_DATE) = DATEDIFF(S1.SUBMISSION_DATE , '2016-03-01')),
(SELECT HACKER_ID FROM SUBMISSIONS S2 WHERE S2.SUBMISSION_DATE = S1.SUBMISSION_DATE 
GROUP BY HACKER_ID ORDER BY COUNT(SUBMISSION_ID) DESC, HACKER_ID LIMIT 1) AS TMP,
(SELECT NAME FROM HACKERS WHERE HACKER_ID = TMP)
FROM
(SELECT DISTINCT SUBMISSION_DATE FROM SUBMISSIONS) S1
GROUP BY SUBMISSION_DATE;

(**) Bài 55:

Imgur

   SET @number = 1;
   SET @divisor = 1;
SELECT GROUP_CONCAT(n SEPARATOR '&')
  FROM (SELECT @number := @number + 1 AS n 
          FROM information_schema.tables AS t1, information_schema.tables AS t2
         LIMIT 1000
       ) AS n1
 WHERE NOT EXISTS(SELECT *
                    FROM (SELECT @divisor := @divisor + 1 AS d
                            FROM information_schema.tables AS t3, information_schema.tables AS t4
                           LIMIT 1000
                         ) AS n2
                   WHERE MOD(n, d) = 0 AND n <> d)

Ngày 01-03-2022

Soạn bài

  1. Tải và cài đặt SQL EXpress 2019: Hướng dẫn cài đặt tại đây

Cách thức viết câu lệnh:

  • Nguyên tắc người viết code: “Tnh tế trong từng câu lệnh”, luôn luôn phải hiểu “Viết ra đoạn code để cho người khác đọc và hiểu được” do đó:

  • Trình bày trong khuôn khổ màn hình ngang máy tính

  • Sử dụng tab khi lùi dòng vào phía trong

  • Trình bày phải có dấu cách sau dấu “,”

  • Trình bày theo khối lệnh, gọn gàng, cách dòng trong khối lệnh cho dễ quan sát

  • Các từ khoá viết hoa: SELECT … FROM

  • Lưu ý đến Performance của đoạn lệnh:

  • Kiểm tra chỉ mục trên tất cả các field trên mệnh đề WHERE and JOIN trong câu lệnh SQL

  • Giới hạn kích thước của bảng dữ liệu làm việc: Kiểm tra các bảng được sử dụng trong câu SELECT để có thể áp dụng lọc qua WHERE

  • Chỉ chọn các field mà trong báo cáo cần tránh thừa thông tin

  • Loại bỏ các phần tính toán trong mệnh đề WHERE và JOIN

  • Đặt Index với các Field hay được truy vấn

  • Đặt kích thước của các field theo nguyên tắc byte: 2^n

  • Đầu mã thủ tục, hàm phải có thông tin chung:

  • Người tạo

  • Ngày khởi tạo

  • Mô tả chung

  • Mỗi lần đoạn mã được sửa đổi phải được ghi chú (Comment) rõ ràng:

  • Người sửa đổi

  • Ngày sửa đổi

  • Nội dung chỉnh sửa

  • Các đoạn lệnh có thuật toán phức tạp cần có ghi chú rõ ràng

  • Các câu ghi chú cần rõ ràng, ngắn gọn, đủ nghĩa, không dài dòng.

Bai tap 1:
CREATE DATABASE Tech;
GO

USE Tech

CREATE TABLE Item(
    ItemCode NVARCHAR(16),
    ItemName NVARCHAR(96),
    Unit NVARCHAR(10),
    ItemType INT,
    IsActive INT,
)

GO 

CREATE TABLE Customer(

)

Học chính thức

Tóm tắt:
  • Bài học đầu tiên: SQL

  • Nếu đạt -> học xml

  • Học về nghiệp vụ

  • Thời gian: 3 tháng

  • xml + nghiệp vụ: Full Time

Chính thức:
  • Chú ý: Tiếp cận các bài toán và thuật toán thực tế

  • Đặt tên: Dấu + -> _, nộp bài đúng thời gian được giao

  • Chú ý: Tìm hiểu về các phiên bản của SQL

  • SQL 2019: Nhiều feature mới mà nhiều bản khác không có, ví dụ: merge

  • Những cái khi quy mô lớn: Link Server, Always On (học sau)

  • Nghiên cứu thêm về mảng Security

  • Chú ý: WHERE và JOIN phải có index và không có xử lý tính toán

  • Chú ý: Không SELECT * khi dữ liệu lớn

Bài 1: Tạo bảng

Đề bài: Tạo bảng có 2 trường là: manhanvientennhanvien

USE buoi1
CREATE TABLE DEMO1(
	manhanvien NVARCHAR(16),
	tennhanvien NVARCHAR(50)
)

/* Bo sung not null*/
--USE buoi1
--CREATE TABLE DEMO2(
--	manhanvien NVARCHAR(16) NOT NULL DEFAULT(''),
--	tennhanvien NVARCHAR(50) NOT NULL DEFAULT('')
--)

/**/
Bài 2: Sử dụng câu lệnh ALTER để thêm một cột socmnd
ALTER TABLE DEMO1 ADD socmnd NVARCHAR(12)

Note: Để xem lại cột ta đã thêm được chưa vào thư mục nhất nút phải để kiểm tra.

Bài 3: DROP bảng
DROP TABLE DEMO1
Bài 4: Sao chép cấu trúc để tạo bảng mới

dbo.DEMO1 -> Script Table as -> CREATE To -> New query Editor Window (Nhấn nút phải)

Bài 5: INSERT dữ liệu (chú ý bổ sung cú pháp)
INSERT INTO DEMO1 (manhanvien, tennhanvien, socmnd) VALUES ('ID1001','Ngo Tan Tri', '201793988')

Note: Chú ý để xem bảng kết quả ta vào: dbo.DEMO1 -> Edit Top 200 rows

Nâng cao: Insert 1 lần 2 thanh ghi:

INSERT INTO DEMO1 (manhanvien, tennhanvien, socmnd) VALUES ('ID1001','Ngo Tan B', '201793918'),('ID1002','Ngo Tan C', '201793999')
SELECT * FROM DEMO1

Note: Chú ý bôi đen rồi f5 để chạy

Bài 6: UPDATE dữ liệu biến đổi số chứng minh nhân dân thành số điện thoại
UPDATE DEMO1 SET socmnd = '0787135926'  WHERE tennhanvien = 'Ngo Tan Tri'
SELECT * FROM DEMO1

Cách 2: Chú ý khi viết xuống dòng (tinh tế)

UPDATE DEMO1 
	SET socmnd = '0787135926'  
	WHERE tennhanvien = 'Ngo Tan Tri'
SELECT * FROM DEMO1
Bài 7: Xoá những thanh ghi không phải là tên mình
DELETE FROM DEMO1 WHERE tennhanvien!='Ngo Tan Tri'
SELECT * FROM DEMO1

Note: Dấu != có thể thay thế bằng <>

Bài 8: Các chú ý trong hàm toán học
PRINT ABS(-10)
PRINT FLOOR(9.9)
PRINT ROUND(1000.999,2)
PRINT ROUND(11.0/3,2)
Bài 9: Xử lý hàm chuỗi
PRINT LEFT('Lê Anh Tuấn',2)
PRINT SUBSTRING('abcdee',1,5)
PRINT REPLACE('ABCDEF','CDEF','aaaaaa')

Chú ý: Để sử dụng tiếng Việt thêm chữ N phía trước: PRINT REPLACE(N'Lê Anh Tuấn',' ','')

Bài tập về nhà (Tự làm)

Bài 1: Lập bảng và insert dữ liệu:

USE Tech

/* Create table Item*/
CREATE TABLE Item (
	ItemCode NVARCHAR(16),
	ItemName NVARCHAR(96),
	Unit NVARCHAR(10),
	ItemType INT,
	IsActive INT
)
/* Create table Customer*/
CREATE TABLE Customer(
	CustomerCode NVARCHAR(16),
	CustomerName NVARCHAR(96),
	CustomerType INT,
	IsActive INT
)

/* Create table AccDoc*/
CREATE TABLE AccDoc(
	DocCode CHAR(2),
	DocNo NVARCHAR(10) NOT NULL PRIMARY KEY,
	DocDate DATETIME,
	CustomerCode NVARCHAR(16),
	DocGroup INT,
	Description NVARCHAR(256),
	IsActive INT
)

/* Create table AccDocDetail*/
CREATE TABLE AccDocDetail(
	DocCode CHAR(2), /*Link DocCode cua AccDoc*/
	DocNo NVARCHAR(10), /*Link DocNo cua AccDoc*/
	ItemCode NVARCHAR(16),
	Quantity NUMERIC(15,3),
	UnitCost NUMERIC(15,5),
	Amount1 NUMERIC(18,2),
	UnitPrice NUMERIC(15,5),
	Amount2 NUMERIC(18,2)
)

/* Create table AccDocDetail*/
CREATE TABLE OpenInventory(
	ItemCode NVARCHAR(16),
	Quantity NUMERIC(15,3),
	Amount NUMERIC(18,2)
)

/* insert data into table Item*/
INSERT INTO Item(ItemCode,ItemName,Unit,ItemType,IsActive) 
	VALUES 
		('NVLC01', N'Máy nén', N'Cái', 1, 1),
		('NVLC02', N'Tôn dày 0.5 mm', N'Kg', 1, 1),
		('NVLC03', N'Ống đồng', 'M', 1, 1),
		('TP01', N'Tủ đông kích thước 1.5*0.7*0.6', N'Cái', 2, 1),
		('TP02', N'Tủ đông kích thước 1.5*0.8*0.8', N'Cái', 2, 1),
		('TP03', N'Tủ mát kích thước 0.8*0.8*1.9', N'Cái', 2, 1)

--SELECT * FROM Item 

/* insert data into table Customer*/
	
INSERT INTO Customer(CustomerCode,CustomerName,CustomerType,IsActive)
	VALUES
		('NCC01', N'Công ty TNHH Vạn Xuân', 2, 1),
		('NCC02', N'Công ty Cổ phần Đại Phát', 2, 1),
		('NCC03', N'Công ty Cổ phần tôn Hòa Phát', 2, 1),
		('KH01', N'Đại lý Cô Tám', 1, 1),
		('KH02', N'Công ty cổ phần đầu tư xây dựng Dacinco', 2, 1),
		('KH03', N'Công ty TNHH cà phê Thắng Lợi', 2, 1),
		('NB01', N'Phi Công Anh', 1, 1),
		('NB02', N'Đàm Văn Đức', 1, 1),
		('NB03', N'Phân xưởng sản xuất', 3, NULL)

--SELECT * FROM Customer

/*insert data into table AccDoc*/

INSERT INTO AccDoc(DocCode, DocNo, DocDate, CustomerCode, DocGroup, Description, IsActive)
	VALUES
		('NM', 'NM001', '01/01/2022', 'NCC01', 1, N'Nhập mua NPL', 1),
		('NM', 'NM002', '01/10/2022', 'NCC02', 1, N'Nhập mua NPL', 1),
		('NM', 'NM003', '01/11/2022', 'NCC01', 1, N'Nhập mua NPL', 1),
		('NM', 'NM004', '01/15/2022', 'NCC03', 1, N'Nhập mua NPL', 1),
		('PX', 'PX001', '01/02/2022', 'NB03', 2, N'Xuất sản xuất', 1),
		('PX', 'PX002', '01/13/2022', 'NB03', 2, N'Xuất sản xuất', 1),
		('PX', 'PX003', '01/22/2022', 'NB03', 2, N'Xuất sản xuất', 1),
		('PX', 'PX004', '01/28/2022', 'NB03', 2, N'Xuất sản xuất', 1),
		('TP', 'TP001', '01/15/2022', 'NB03', 1, N'Nhập thành phẩm', 1),
		('TP', 'TP002', '01/31/2022', 'NB03', 1, N'Nhập thành phẩm', 1),
		('HD', 'HD001', '01/05/2022', 'KH01', 2, N'Xuất bán hàng', 1),
		('HD', 'HD002', '01/06/2022', 'KH03', 2, N'Xuất bán hàng', 1),
		('HD', 'HD003', '01/10/2022', 'KH02', 2, N'Xuất bán hàng', 1),
		('HD', 'HD004', '01/12/2022', 'KH01', 2, N'Xuất bán hàng', 1),
		('HD', 'HD005', '01/16/2022', 'KH02', 2, N'Xuất bán hàng', 1),
		('HD', 'HD006', '01/18/2022', 'KH03', 2, N'Xuất bán hàng', 1),
		('HD', 'HD007', '01/23/2022', 'KH01', 2, N'Xuất bán hàng', 1),
		('HD', 'HD008', '01/31/2022', 'KH03', 2, N'Xuất bán hàng', 1)
	
--SELECT * FROM AccDoc	

/* insert data into table AccDocDetail*/

INSERT INTO AccDocDetail(DocCode, DocNo, ItemCode, Quantity, UnitCost, Amount1, UnitPrice, Amount2)
	VALUES
		('NM', 'NM001', 'NVLC01', 100.00, 3099000.00, 309900000, NULL, NULL ),
		('NM', 'NM001', 'NVLC02', 999.95, 29956.35, 29954852, NULL, NULL),
		('NM', 'NM002', 'NVLC01', 50.00, 3050000.00, 152500000, NULL, NULL),
		('NM', 'NM002', 'NVLC02', 200.33, 29956.55, 6001196, NULL, NULL),
		('NM', 'NM002', 'NVLC03', 2000.00, 105987.92, 211975840, NULL, NULL),
		('NM', 'NM003', 'NVLC01', 60.00, 3050000.00, 183000000, NULL, NULL),
		('NM', 'NM003', 'NVLC02', 100.00, 29956.55, 2995655, NULL, NULL),
		('NM', 'NM003', 'NVLC03', 150.00, 105987.92, 15898188, NULL, NULL),
		('NM', 'NM004', 'NVLC01', 90.00, 3050000.00, 274500000, NULL, NULL),
		('NM', 'NM004', 'NVLC02', 300.00, 29956.55, 8986965, NULL, NULL),
		('NM', 'NM004', 'NVLC03', 200.00, 105987.92, 21197584, NULL, NULL),
		('PX', 'PX001', 'NVLC01', 90.00, NULL, NULL, NULL, NULL),
		('PX', 'PX001', 'NVLC02', 500.00,NULL, NULL, NULL, NULL),
		('PX', 'PX001', 'NVLC03', 400.00, NULL, NULL, NULL, NULL),
		('PX', 'PX002', 'NVLC01', 50.00, NULL, NULL, NULL, NULL),
		('PX', 'PX002', 'NVLC02', 200.33, NULL, NULL, NULL, NULL),
		('PX', 'PX002', 'NVLC03', 1000.00, NULL, NULL, NULL, NULL),
		('PX', 'PX003', 'NVLC01', 100.00, NULL, NULL, NULL, NULL),
		('PX', 'PX003', 'NVLC02', 150.00, NULL, NULL, NULL, NULL),
		('PX', 'PX003', 'NVLC03', 200.00, NULL, NULL, NULL, NULL),
		('PX', 'PX004', 'NVLC01', 90.00, NULL, NULL, NULL, NULL),
		('PX', 'PX004', 'NVLC02', 320.00, NULL, NULL, NULL, NULL),
		('PX', 'PX004', 'NVLC03', 170.00, NULL, NULL, NULL, NULL),
		('TP', 'TP001', 'TP01', 400.00, NULL, NULL, NULL, NULL),
		('TP', 'TP001', 'TP02', 500.00, NULL, NULL, NULL, NULL),
		('TP', 'TP001', 'TP03', 700.00, NULL, NULL, NULL, NULL),
		('TP', 'TP002', 'TP01', 300.00, NULL, NULL, NULL, NULL),
		('TP', 'TP002', 'TP02', 200.00, NULL, NULL, NULL, NULL),
		('TP', 'TP002', 'TP03', 200.00, NULL, NULL, NULL, NULL),
		('HD', 'HD001', 'TP02', 100.00, NULL, NULL, 11000000, 1100000000),
		('HD', 'HD001', 'TP03', 300.00, NULL, NULL, 12000000, 3600000000),
		('HD', 'HD002', 'TP01', 50.00, NULL, NULL, 10000000, 500000000),
		('HD', 'HD002', 'TP03', 150.00, NULL, NULL, 12000000,1800000000),
		('HD', 'HD003', 'TP01', 50.00, NULL, NULL, 10000000, 500000000),
		('HD', 'HD003', 'TP02', 100.00, NULL, NULL, 11000000, 1100000000),
		('HD', 'HD004', 'TP01', 90.00, NULL, NULL, 10000000, 900000000),
		('HD', 'HD004', 'TP02', 270.00, NULL, NULL, 11000000, 2970000000),
		('HD', 'HD004', 'TP03', 140.00, NULL, NULL, 12000000, 1680000000),
		('HD', 'HD005', 'TP02', 100.00, NULL, NULL, 11000000, 1100000000),
		('HD', 'HD005', 'TP03', 300.00, NULL, NULL, 12000000, 3600000000),
		('HD', 'HD006', 'TP01', 50.00, NULL, NULL, 10000000, 500000000),
		('HD', 'HD006', 'TP03', 150.00, NULL, NULL, 12000000, 1800000000),
		('HD', 'HD007', 'TP01', 50.00, NULL, NULL, 10000000, 500000000),
		('HD', 'HD008', 'TP02', 100.00, NULL, NULL, 11000000, 1100000000),
		('HD', 'HD008', 'TP01', 90.00, NULL, NULL, 10000000, 900000000),
		('HD', 'HD008', 'TP02', 270.00, NULL,NULL, 11000000, 2970000000),
		('HD', 'HD008', 'TP03', 140.00, NULL, NULL, 12000000, 1680000000)

--SELECT * FROM AccDocDetail

/* insert data into table OpenInventpry*/

INSERT INTO OpenInventory(ItemCode, Quantity, Amount)
	VALUES 
		('NVLC01', 1000, 3000000000),
		('NVLC02', 1500, 46500000),
		('NVLC03', 2000, 210000000),
		('TP01', 500, 2000000000),
		('TP02', 400, 2000000000),
		('TP03', 600, 2520000000)

--SELECT * FROM OpenInventory

Bài 2: Bài tập về hàm

/* Bai tap ve ham*/
USE Tech

/* Bai 1: Hien thi thong tin: Bang chi tiet chung tu voi nhung vat tu co Quantity khong phai la so nguyen*/
SELECT * FROM AccDocDetail WHERE FLOOR(Quantity) != CEILING(Quantity)

/*Bai 2: Cho mot chuoi ho va ten: Lay ra ten dem va ten*/

DECLARE @_ho_va_ten NVARCHAR(50);

DECLARE @_empty_first_pos INT;

DECLARE @_empty_second_pos INT;

DECLARE @_length INT;

SELECT @_ho_va_ten = N'     Ngo Tan Tri   ' ; 

SELECT @_ho_va_ten =  LTRIM(@_ho_va_ten)

SELECT @_ho_va_ten =  RTRIM(@_ho_va_ten)

PRINT('Toi len la:  ' + @_ho_va_ten)

SELECT @_length = LEN(@_ho_va_ten) ; 

SELECT @_empty_first_pos = CHARINDEX(' ',@_ho_va_ten,1) ; 

SELECT @_empty_second_pos = CHARINDEX(' ',@_ho_va_ten,@_empty_first_pos+1) ; 

PRINT('Ten dem la: ' + SUBSTRING(@_ho_va_ten,@_empty_first_pos+1,@_empty_second_pos-(@_empty_first_pos+1)))
PRINT('Ten la: ' + SUBSTRING(@_ho_va_ten,@_empty_second_pos+1,@_length-@_empty_second_pos))
--PRINT(@_empty_second_pos)

/*Bai 3: Cho chuoi @_A, cat ky tu chuoi @_A de hien thi du lieu theo tung dong*/

DECLARE @_A NVARCHAR (32); 

DECLARE @_leng INT;

DECLARE @_pos_ INT;

SELECT @_A = N'Bố, Mẹ, Anh, Chị' 

/*In Bo*/

SELECT @_leng = LEN(@_A)

--PRINT(@_leng)

SELECT @_pos_ = CHARINDEX(',',@_A,1)

PRINT(SUBSTRING(@_A,1,@_pos_-1))

SELECT @_A = SUBSTRING(@_A,@_pos_+2,@_leng - (@_pos_+1))

--PRINT(@_A)

/*In Me */

SELECT @_leng = LEN(@_A)

--PRINT(@_leng)

SELECT @_pos_ = CHARINDEX(',',@_A,1)

PRINT(SUBSTRING(@_A,1,@_pos_-1))

SELECT @_A = SUBSTRING(@_A,@_pos_+2,@_leng - (@_pos_+1))

--PRINT(@_A)

/*In Anh*/

SELECT @_leng = LEN(@_A)

--PRINT(@_leng)

SELECT @_pos_ = CHARINDEX(',',@_A,1)

PRINT(SUBSTRING(@_A,1,@_pos_-1))

SELECT @_A = SUBSTRING(@_A,@_pos_+2,@_leng - (@_pos_+1))

/*In Chi*/

PRINT(@_A)

/*Bai 4: Hien thi danh muc vat tu ma co ten vat tu trong chuoi danh sach @_List_Ten_VT = 'May, Dong, Ton'*/

DECLARE @_List_Ten_VT  NVARCHAR(50) ;

SELECT @_List_Ten_VT = N'Máy,Đồng,Tôn' ;

DECLARE @_bien1 NVARCHAR(36);

DECLARE @_bien2 NVARCHAR(36);

DECLARE @_bien3 NVARCHAR(36);

DECLARE @_vtd INT;

DECLARE @_vtc INT;

SELECT @_List_Ten_VT = @_List_Ten_VT + ',';

/* Tach lan 1*/

SELECT @_vtd = 0 ;

SELECT @_vtc = CHARINDEX(',',@_List_Ten_VT,@_vtd+1)

SELECT @_vtd = @_vtd +1  ;

SELECT @_bien1 = SUBSTRING(@_List_Ten_VT,@_vtd,@_vtc-@_vtd)

PRINT(@_bien1)

/* Tach lan 2*/

SELECT @_vtd = @_vtc ;

SELECT @_vtc = CHARINDEX(',',@_List_Ten_VT,@_vtd+1)

SELECT @_vtd = @_vtd +1 

SELECT @_bien2 = SUBSTRING(@_List_Ten_VT,@_vtd,@_vtc-@_vtd)

PRINT(@_bien2)

/* Tach lan 3*/

SELECT @_vtd = @_vtc ;

SELECT @_vtc = CHARINDEX(',',@_List_Ten_VT,@_vtd+1)

SELECT @_vtd = @_vtd +1 

SELECT @_bien3 = SUBSTRING(@_List_Ten_VT,@_vtd,@_vtc-@_vtd)

PRINT(@_bien3)

--PRINT(CHARINDEX('Đồng', @_List_Ten_VT,1))

SELECT * FROM Item WHERE (CHARINDEX(@_bien1,ItemName)!=0 OR CHARINDEX(@_bien2,ItemName)!=0 OR CHARINDEX(@_bien3,ItemName)!=0)

/*Bai 5: Hien thi ky tu dau tien viet hoa va ky tu khac viet thuong trong chuoi ten co 3 tu 'ninH ngỌc hiếU'*/


DECLARE @_ten NVARCHAR(36) ;

DECLARE @_first NVARCHAR(36) ;

DECLARE @_second NVARCHAR(36) ;

DECLARE @_pos_start INT;

DECLARE @_pos_end INT;

DECLARE @_res NVARCHAR(36);

SELECT @_ten = N'ninH ngỌc hiếU' 

/* Start lap*/

SELECT @_res = ''

SELECT @_pos_start = 0;

SELECT @_ten =  @_ten + ' '

SELECT @_pos_end = CHARINDEX(' ',@_ten,@_pos_start+1)

SELECT @_pos_start = @_pos_start +1 ;

SELECT @_res = @_res + UPPER(SUBSTRING(@_ten,@_pos_start,1)) + LOWER(SUBSTRING(@_ten,@_pos_start+1,@_pos_end-@_pos_start-1))

SELECT @_pos_start = @_pos_end 

--PRINT(@_res)

SELECT @_res = @_res+' ' ; 

/*Lap lan 2*/

SELECT @_pos_end = CHARINDEX(' ',@_ten,@_pos_start+1)

SELECT @_pos_start = @_pos_start +1 ;

SELECT @_res = @_res + UPPER(SUBSTRING(@_ten,@_pos_start,1)) + LOWER(SUBSTRING(@_ten,@_pos_start+1,@_pos_end-@_pos_start-1))

SELECT @_pos_start = @_pos_end 

--PRINT(@_res)

SELECT @_res = @_res+' ' ;

/*Lap lan 3*/

SELECT @_pos_end = CHARINDEX(' ',@_ten,@_pos_start+1)

SELECT @_pos_start = @_pos_start +1 ;

SELECT @_res = @_res + UPPER(SUBSTRING(@_ten,@_pos_start,1)) + LOWER(SUBSTRING(@_ten,@_pos_start+1,@_pos_end-@_pos_start-1))

SELECT @_pos_start = @_pos_end 

PRINT(@_res)

/* Bai 6: Hien thi ky tu dau tien viet hoa va ky tu khac viet thuong trong chuoi ten 'Hai hoa vinH le nguyen quang'*/

DECLARE @_pten NVARCHAR(36) ;

DECLARE @_pfirst NVARCHAR(36) ;

DECLARE @_psecond NVARCHAR(36) ;

DECLARE @_ppos_start INT;

DECLARE @_ppos_end INT;

DECLARE @_pres NVARCHAR(36);

SELECT @_pten = N'Hải hòa vinH lê nguyên quang' 

/* Start lap*/

SELECT @_pres = ''

SELECT @_ppos_start = 0;

SELECT @_pten =  @_pten + ' '

SELECT @_ppos_end = CHARINDEX(' ',@_pten,@_ppos_start+1)

SELECT @_ppos_start = @_ppos_start +1 ;

SELECT @_pres = @_pres + UPPER(SUBSTRING(@_pten,@_ppos_start,1)) + LOWER(SUBSTRING(@_pten,@_ppos_start+1,@_ppos_end-@_ppos_start-1))

SELECT @_ppos_start = @_ppos_end 

--PRINT(@_res)

SELECT @_pres = @_pres+' ' ; 

/*Lap lan 2*/

SELECT @_ppos_end = CHARINDEX(' ',@_pten,@_ppos_start+1)

SELECT @_ppos_start = @_ppos_start +1 ;

SELECT @_pres = @_pres + UPPER(SUBSTRING(@_pten,@_ppos_start,1)) + LOWER(SUBSTRING(@_pten,@_ppos_start+1,@_ppos_end-@_ppos_start-1))

SELECT @_ppos_start = @_ppos_end 

--PRINT(@_res)

SELECT @_pres = @_pres+' ' ;

/*Lap lan 3*/

SELECT @_ppos_end = CHARINDEX(' ',@_pten,@_ppos_start+1)

SELECT @_ppos_start = @_ppos_start +1 ;

SELECT @_pres = @_pres + UPPER(SUBSTRING(@_pten,@_ppos_start,1)) + LOWER(SUBSTRING(@_pten,@_ppos_start+1,@_ppos_end-@_ppos_start-1))

SELECT @_ppos_start = @_ppos_end 

SELECT @_pres = @_pres+' ' ;

--PRINT(@_pres)

/*Lap lan 4*/

SELECT @_ppos_end = CHARINDEX(' ',@_pten,@_ppos_start+1)

SELECT @_ppos_start = @_ppos_start +1 ;

SELECT @_pres = @_pres + UPPER(SUBSTRING(@_pten,@_ppos_start,1)) + LOWER(SUBSTRING(@_pten,@_ppos_start+1,@_ppos_end-@_ppos_start-1))

SELECT @_ppos_start = @_ppos_end 

SELECT @_pres = @_pres+' ' ;

--PRINT(@_pres)

/*Lap lan 5*/

SELECT @_ppos_end = CHARINDEX(' ',@_pten,@_ppos_start+1)

SELECT @_ppos_start = @_ppos_start +1 ;

SELECT @_pres = @_pres + UPPER(SUBSTRING(@_pten,@_ppos_start,1)) + LOWER(SUBSTRING(@_pten,@_ppos_start+1,@_ppos_end-@_ppos_start-1))

SELECT @_ppos_start = @_ppos_end 

SELECT @_pres = @_pres+' ' ;

--PRINT(@_pres)

/*Lap lan 6*/

SELECT @_ppos_end = CHARINDEX(' ',@_pten,@_ppos_start+1)

SELECT @_ppos_start = @_ppos_start +1 ;

SELECT @_pres = @_pres + UPPER(SUBSTRING(@_pten,@_ppos_start,1)) + LOWER(SUBSTRING(@_pten,@_ppos_start+1,@_ppos_end-@_ppos_start-1))

SELECT @_ppos_start = @_ppos_end 

--SELECT @_pres = @_pres+' ' ;

PRINT(@_pres)

/*TEST*/

DECLARE @_d NUMERIC(15,3) 

SELECT @_d = 999.001 ;

PRINT(FLOOR(@_d))

PRINT(CEILING(@_d))

PRINT(@_d % 1)

BÀI TẬP VỀ NHÀ: LÀM PRINT

THỨ 6 HỌC LẠI (NGÀY 4/3/2022)


Soạn bài buổi 2

IV. Định nghĩa biến trong SQL và câu lệnh EXECUTE (“Chuỗi”)
  1. Biến trong SQL
  • Để khai báo biến trong SQL Server, ta sử dụng câu lệnh DECLARE, cú pháp như sau:

DECLARE @<Tên biến> <Kiểu dữ liệu của biến> [= Giá trị gán cho biến]

  • : Tên của biến. Đối với Bravo thì yêu cầu có dấu gạch '_' trước tên của biến
  • : Kiểu dữ liệu định nghĩa cho biến
  • Ví dụ: Để khai báo biến ItemCode thì khai báo như sau:

DECLARE @_Itemcode NVARCHAR(16)

  1. Câu lệnh EXECUTE('Chuỗi')
  • Cấu trúc EXECUTE('SELECT * FROM Item')

  • Nguyên tắc biến câu lệnh Query SQL thành chuỗi trong câu lệnh EXECUTE():

  • Thêm 2 dấu nháy đơn vào đằng trước và đằng sau câu lệnh

  • Với mỗi dấu nháy đơn ở câu lệnh Query SQL thông thường khi vào chuỗi để sử dụng trong Câu lệnh EXECUTE thì sẽ thêm 1 dấu nháy nữa

Ví dụ:

SELECT * FROM Item WHERE ItemCode = 'TP01'

  • Trường hợp muốn công ký tự đặc biệt vào chuỗi thì dùng hàm CHAR(Mã KeyAscii)

Ví dụ:

  • CHAR(13) -> Ký tự Enter

  • CHAR(39) -> Ký tự nháy đơn

V. Hàm ngày tháng
  1. Hàm ngày tháng
  • GETDATE(): Trả về ngày giờ hiện hành

  • GETUTCDATE(): Trả về ngày và giờ UTC hiện tại

  • CURRENT_TIMESTAMP: Trả về ngày giờ hiện hành

  • DATEADD(interval, number, date): trả về một ngày mà sau đó một khoảng thời gian/ngày nhất định đã được thêm vào

  • interval: Nó có thể là một trong những giá trị sau

year, yyyy,yy - Khoảng thời gian năm

quarter,qq,q - Khoảng thời gian quý

month, mm,m - Khoảng thời gian tháng

dayofyear - Ngày trong năm

day,dy,y - Khoảng thời gian trong ngày

week, ww,wk - Khoảng thời gian trong tuần

weekday, dw,w - Khoảng thời gian các ngày trong tuần

hour, hh - Khoảng thời gian chờ

minute, mi,n - Khoảng thời gian phút

second, ss, s - Khoảng thời gian giây

millisecond, ms - Khoảng thời gian micro giây

  • number: Số lượng khoảng thời gian muốn thêm

  • date: Ngày mà khoảng thời gian được thêm vào

Note: SET DATEFORMAT DMY

  • Ví dụ:
SELECT DATEADD(year, 3, '2022/04/06')
--Ket qua: '2025-06-04 00:00:00.000'
SELECT DATEADD(yyyy, 4, '2022/04/06')
--Ket qua: '2026-06-04 00:00:00.000
SELECT DATEADD(yy, 9, '2022/04/06');
--Ket qua: '2031-06-04 00:00:00.000'
SELECT DATEADD(year, -2, '2022/04/06');
--Ket qua: '2020-06-04 00:00:00.000'
SELECT DATEADD(month, 8, '2022/04/06');
--Ket qua: '2023-02-04 00:00:00.000'
SELECT DATEADD(month, -6, '2022/04/06');
--Ket qua: '2021-12-04 00:00:00.000'
SELECT DATEADD(day, 4, '2022/04/06');
--Ket qua: '2022-06-08 00:00:00.000'
SELECT DATEADD(day, -5, '2022/04/06');
--Ket qua: '2022-05-30 00:00:00.000'

DATEDIFF(interval, date1, date2): trả về chênh lệch giữa hai giá trị ngày, dựa trên khoảng thời gian được chỉ định.

Bài tập về nhà
/* Bài 1: Hiển thị các chứng từ phiếu xuất có phát sinh từ ngày hiện tại đến 180 ngày về trước gồm: DocNo, DocDate, DocGroup, Description */
USE Tech
SELECT DocNo,DocDate,DocGroup,Description FROM AccDoc WHERE DATEDIFF(day,DocDate ,GETDATE()) <=180

/* Bài 2: HIển thị các phiếu được bán vào thứ 4 ngày 5*/

SELECT * FROM AccDoc WHERE DATEPART(day,DocDate) = 5 AND DATEPART(WEEKDAY,DocDate)=4 AND DocCode = 'HD'


/* Bài 3: Sử dụng các hàm ngày tháng để hiển thị thông tin của bảng chứng gồm: DocCode, DocNo, DocDate, Thang, Quy, Nam, DocGroup, Description */

--PRINT(DATEPART(dw,GETDATE())) 

SELECT 
		DocCode, DocNo, DocDate,
		DATEPART(MONTH,DocDate) AS N'Tháng',
		DATEPART(QUARTER,DocDate) AS N'Quý',
		DATEPART(YEAR,DocDate) AS N'Năm',
		DocGroup,
		Description
FROM AccDoc 

/* Bài 4: Cho mot ngay bat ky */

DECLARE @_Date DATE

DECLARE @_FirstDate DATE

DECLARE @_SecondDate DATE

DECLARE @_FirstDateTwo DATE

DECLARE @_SecondDateTwo DATE

DECLARE @_tmp_Date DATE

SELECT @_Date = '02-28-2024'

SELECT @_tmp_Date = @_Date

/* Bai 4.1: Lay ra ngay dau thang va ngay cuoi thang*/
PRINT ('Bai 4.1: ')
--PRINT @_Date

/* first day of month*/

SELECT @_FirstDate = DATEADD(m, DATEDIFF(m, 0, @_Date), 0)

-- Get lastday of month

SELECT @_Date = DATEADD(month, 1, @_Date)

SELECT @_Date = DATEADD(m, DATEDIFF(m, 0, @_Date), 0)

SELECT @_SecondDate = DATEADD(day, DATEDIFF(day, 0, @_Date)-1, 0)

--PRINT(@_Date)

PRINT (@_FirstDate)

PRINT (@_SecondDate)

/* Bai 4.2: Lay ngay dau thang cung ky năm trước và ngày cuối tháng cùng kỳ năm trước*/

PRINT ('Bai 4.2: ')

SELECT @_Date = @_tmp_Date

SELECT @_Date = DATEADD(year,-1,@_Date)

--PRINT(@_Date)

/* Previous year and first day of month*/

SELECT @_FirstDateTwo = DATEADD(m, DATEDIFF(m, 0, @_Date), 0)

/* Previous year and last day of month*/

SELECT @_Date = DATEADD(month, 1, @_Date)

SELECT @_Date = DATEADD(m, DATEDIFF(m, 0, @_Date), 0)

SELECT @_SecondDateTwo = DATEADD(day, DATEDIFF(day, 0, @_Date)-1, 0)

PRINT (@_FirstDateTwo)

PRINT (@_SecondDateTwo)

/* Bai cua Le Kieu Linh*/

DECLARE @_CheckDate DATETIME
SELECT @_CheckDate = '2024/02/28'

SELECT	DATEADD(DD, - (DAY(@_CheckDate) - 1), @_CheckDate) AS First_Day_Of_Month,
		DATEADD(DD, - (DAY(DATEADD(MM, 1, @_CheckDate))), DATEADD(MM, 1, @_CheckDate)) AS Last_Day_Of_Month

SELECT	DATEADD(MM, -12, DATEADD(DD, - (DAY(@_CheckDate) - 1), @_CheckDate)) AS FDOM_Of_Same_Period_Last_Year,
		DATEADD(MM, -12, DATEADD(DD, - (DAY(DATEADD(MM, 1, @_CheckDate))), DATEADD(MM, 1, @_CheckDate))) AS LDOM_Of_Same_Period_Last_Year


Soạn bài buổi 3

VI. Ràng buộc, chỉ mục, hàm và các lệnh hỗ trợ truy vấn
  1. Ràng buộc

1.1. Tạo Primary Key

Khoá chính là tập hợp một hoặc nhiều column giúp phân biệt các record trong một table, đây là thông tin rất quan trọng bởi nếu thiếu nó thì lược đồ CSDL sẽ không hình thành.

Ví dụ bảng Item thì thường ta sẽ có column ItemCode dùng để nhận diện các Code, ItemName có thể bị trùng nhưng mã ItemCode thì không thể trùng.

Đặc điểm của khoá chính như sau:

  • Có thể thiết lập khoá chính bằng một hoặc nhiều column, trong thực tế thì nên 1 column.

  • Khoá chính không được NULL, và là duy nhất (unique)

  • Khoá chính nếu là kiểu số nguyên thì nên thiết lập tăng tự động sẽ giúp tối ưu database.

Chúng ta có hai cách tạo primary key, thứ nhất là tạo trực tiếp ở lệnh CREATE TABLE và thứ hai là sử dụng lệnh ALTER TABLE

*** Tạo trực tiếp ở lệnh CREATE TABLE

Cách này có hai cú pháp như sau:

Cú pháp 1:

  • CREATE TABLE table_name(column_1 data_type PRIMARY KEY,...)

Cú pháp 2:

  • CREATE TABLE table_name(column_1 data_type, column_2 data_type,...) PRIMARY KEY(column_1,column_2))

Ví dụ: Bảng Item 1 có khoá chính là ItemCode thì khi tạo bảng như sau:

CREATE TABLE Item(
	ItemCode NVARCHAR(16) NOT NULL DEFAULT('') PRIMARY KEY,
	ItemName NVARCHAR(96) NOT NULL DEFAULT(''),
	Unit NVARCHAR(10) NOT NULL DEFAULT(''),
	ItemType INT NOT NULL DEFAULT((0)),
	IsActive INT NOT NULL DEFAULT((1))
)

*** Tạo bằng lệnh ALTER TABLE

Cú pháp: ALTER TABLE Table_Name ADD PRIMARY KEY(Column_1, Column_2)

Ví dụ: ALTER TABLE Item ADD PRIMARY KEY(ItemCode)

1.2. Khoá ngoại Foreign Key

  • Khoá ngoại hay còn gọi là Foreign Key, đây là mối liên kết giữa hai bảng với nhau tạo thành một lược đồ cơ sở dữ liệu quan hệ.

  • Giả sử ta có hai bảng : AccDocAccDocDetail, bảng AccDoc lưu trữ danh sách các chứng từ, bảng AccDocDetail lưu danh sách chi tiết của chứng từ. Dẫn đến có mối liên hệ chi tiết chứng từ trong AccDocDetail thuộc một chứng từ nào AccDoc.

  • Để thể hiện mỗi liên hệ này