closest value and last value problem - php

I have a data table having fields(date,company,data_id,rank etc)..as problem is related to these fields that's why showing these fields only. suppose table is:
data_id | company | date | rank
1 | google | 23/10/2010| 1
2 | yahoo | 23/10/2010| 4
3 | msn | 23/10/2010| 8
4 | google | 27/10/2010| 3
5 | yahoo | 27/10/2010| 1
6 | msn | 27/10/2010| 6
7 | google | 29/10/2010| 1
8 | yahoo | 29/10/2010| 4
9 | msn | 29/10/2010| 3
...and so on
PROBLEM 1:
there are many users-suppose there are user1,user2,user3. All have their [my_company] in session.
Now, I have to display only those entries which are made last(can be done by any user on any date) as per company.
Example: my_company[user1-yahoo,user2-google,user3-msn]
user's [my_company] only display his company's value,nothing else..but only value entered last(on date-here 29/10/2010).
Data is added for any company by any user on any date.now as this process will continue, entries will grow.HOW CAN I FIND WHICH DATE IS LAST(specific to a company)?
PROBLEM 2:
how to find closest date to a specific date?

... where `company_name` = 'companyName' order by `date` desc limit 1
and
... between mydate - INTERVAL and mydate + INTERVAL
http://dev.mysql.com/doc/refman/5.5/en/date-and-time-functions.html

when you create session variable sort data by date so you will have order in my_company
once you have ordered list you can figure out which date belongs to which date
or
while adding data to my_company add id
you can find closest date by
SELECT date FROM table ORDER BY abs(now() - date) LIMIT 1
http://dev.mysql.com/doc/refman/5.0/en/mathematical-functions.html#function_abs

Related

Handle Membership plans in the renewal month

I am working on a membership portal using Laravel.
Membership has different categories like
1) Single
2) Adult
3) Family
and all types with different prices.
I have a plans table and plans_subscription table
Plans table has membership type information and plans_subscription table has the following fields
id | user_id | plan_id | starts_on | expires_on
Now the membership runs on a yearly basis and renewal for next year only opens a month before the end of the year.
I insert one row for each renewal like below
id | user_id | plan_id | starts_on | expires_on
1 | 23 | 1 | 01-01-2018| 31-12-2018
2 | 23 | 1 | 01-01-2019| 31-12-2019
Some user may decide to change the plan for the next year like following
id | user_id | plan_id | starts_on | expires_on
3 | 24 | 1 | 01-01-2018| 31-12-2018
4 | 24 | 2 | 01-01-2019| 31-12-2019
How do I show the user that they are still a member for the current year under a different plan and from next year on they will under different subscription?
How should I get the information that a user has already has paid for the next year and display get their correct membership expiry date?
Is it a good idea to insert separate rows for each renewal or should I just extend the expires_on date?
Thank you
In your case, you need to insert seperate rows because you need to show the user what subscription he's in for next year. It's a good thing because you have a expire_on column. In that you can identify the subscription of the users and also you can create a block of data for the subscription history of the user if you insert seperate rows.

How to get webstore top donator per month?

I created a webstore and I put a top donator per month.
My problem is, how I can get "top donator"?
I try in SQL query MAX(money) but have problem on example:
test 250
test2 3
And say max value is 3
My table:
Date | username | money
2016/7 | tg95 | 10
2016/7 | test | 15
How I can get the top donator perm amount?
Here is a table config example:
date | username | money
2016/7 | test | 10
2016/7 | test2 | 15
2016/7 | test3 | 9
on this example max value is test2 = 15. Maybe more simple is get date (per month) and get a max value on money.
Try:
SELECT username FROM Table1 ORDER BY money DESC LIMIT 1;
SQL FIDDLE
If you want to select username of max donator money you can use this sql
select username, money
from youtablename
where money= (
select max(money)
from youtablename
)

Join Row to Previous Closest Date Row

Database data:
id | account | date | random_data
1 | 1 | 01/01/2013 | qw
2 | 2 | 05/01/2013 | er
3 | 2 | 09/01/2013 | ty
4 | 1 | 05/01/2013 | ui
5 | 2 | 11/01/2013 | op
6 | 1 | 12/01/2013 | as
Hi, so let's say I want the records starting from 05/01/2013 - note that prev_date for the 1st row still shows an earlier date than 05/01 meaning that the whole table still needs to be searched.
Result data:
account | cur_date | random_data | prev_date | prev_rand_data
1 | 05/01/2013 | ui | 01/01/2013 | qw
1 | 12/01/2013 | as | 05/01/2013 | ui
2 | 05/01/2013 | er | null | null
2 | 09/01/2013 | ty | 05/01/2013 | er
2 | 11/01/2013 | op | 09/01/2013 | ty
So I'm not sure what is the best, most optimized query I could use for this. I'm not opposed to a php solution but not sure how much better that would be. Some ideas I've considered:
Some sort of join on the same table - not sure how though
Sub queries on the select -
select date as cur_date
, (select max(date)
from table
where date < cur_date
group by account)
as prev_date... - this seems like it could be incredibly intensive
Session variables - set a session variable on each row which will be the previous data for the next row e.g.
select date as cur_date
, #prev_date as prev_date
, #prev_date:=date...
Has anyone had any experience with a problem like this and was there a good solution? Are there any positives negatives with any of the ideas I have that could cause problems in the future?
I would use a combination of sql and application code. Since I am not a php programmer, I will only describe the logic to use for the application part.
First the query.
select account, date, random_data
from thetable
where date >= YourDateVariable
union
select account, date, random_data
from thetable join
(select account acc, max(date) maxdate
from thetable
where date <= YourDateVariable
group by account) x on account = acc and date = max(date)
where date <= YourDateVariable
order by account, date
For the application code, do this:
Set a variable called ThisAccount to 0.
Set a row counter variable to 0.
Create an empty 2D array
Start looping through your query results
Put the account value and random data into the first two columns
of the next available row of the array
Compare the account value to the value of the ThisAccount variable.
If they are the same, get the previous date and random data from
the previous row in the array.
Set the ThisAccount variable to the current account value.
Increment your row counter variable
End of loop.

PHP MYSQL Detect if new row is added

Any Idea how can I identify if there is new client added on my database.
I was thinking about identifying it thru date_added field.
id client_name date_added
---------------------------------
1 ABC 2013-01-02
2 XYZ 2013-01-03
3 EFG 2013-01-02
4 HIJ 2013-01-05
as you can see a new client added HIJ on 2013-01-05.
I was looking with this kind of result:
Client List
Total NO: 4
New Client
Total No: 1
Client Name: HIJ
add a field new to the table, default it to 1, on page load use that for the select and set it to 0 to indicate its not longer new.
It's hard to tell but based on your comment ...my reference date is 1 month interval... you might be looking for something like this
SELECT id, client_name, new_count, total_count
FROM
(
SELECT id, client_name
FROM clients
WHERE date_added BETWEEN CURDATE() - INTERVAL 1 MONTH AND CURDATE()
) c CROSS JOIN
(
SELECT
(
SELECT COUNT(*) new_count
FROM clients
WHERE date_added BETWEEN CURDATE() - INTERVAL 1 MONTH AND CURDATE()
) new_count,
(
SELECT COUNT(*) total_count
FROM clients
) total_count
) t
Obviously you can easily change CURDATE() with any other reference date in the past in this query and you get results for that date.
Lets assume that you have following sample data
+------+-------------+------------+
| id | client_name | date_added |
+------+-------------+------------+
| 1 | ABC | 2013-05-13 |
| 2 | XYZ | 2013-06-13 |
| 3 | EFG | 2013-06-13 |
| 4 | HIJ | 2013-08-11 |
+------+-------------+------------+
and today is 2013-08-13 then the output from the query will be
+------+-------------+-----------+-------------+
| id | client_name | new_count | total_count |
+------+-------------+-----------+-------------+
| 4 | HIJ | 1 | 4 |
+------+-------------+-----------+-------------+
You could remember, in your webpage or PHP script, the highest ID value previously seen. Or the highest timestamp (better than a date) previously seen.
I prefer ID or Version numbers for concurrency-related stuff (locking, finding the latest etc) -- since they should be defined to be ascending, can't suffer "same millisecond" collisions, and are more efficient.
I assume you're going to hold the "state" of your application (as to what the user has seen) in hidden fields in the form, or somesuch. This would then track the "last seen" and allow you to identify "newly added" since the last pageview.
If you expect to identify newly added when coming from a different page or logging onto the application, you'll need to store the "state" in the database instead.
That depends on what you consider NEW. You have to define what you're going to compare the records against (reference date). Once you define it, you could use a query like the following:
SELECT * FROM client WHERE date_added >= '$date'
where $date is the reference date.

PHP/MYSQL group and count by distinct dates and users

I'm trying to wrap my head around how to get a distinct count of days a user logged in, when the db has each login session stored with a time and date stamp (DATETIME column). EG:
USERID | TIME | BOUGHT
--------------------------
4 | 2012-07-16 04:44:52 | 3
4 | 2012-07-16 04:45:52 | 2
5 | 2012-07-16 04:54:52 | 5
4 | 2012-07-18 04:44:52 | 3
4 | 2012-07-18 04:45:52 | 2
4 | 2012-07-21 04:54:52 | 5
I want to search for how many times user 4 bought from the site - and the query should return 3 (because user 4 visited the site a total of 3 days). Do I have to use a PHP/MYSQL combination or can I do it in SQL?
SELECT USERID, COUNT(DISTINCT DATE(TIME)) FROM my_table GROUP BY USERID
See it on sqlfiddle.

Categories