Turn to recursive method in common-lisp - lisp

This is the coordinates for 3 boards of tic tac toe connected between themselves and i would like to know how can i reduce this code making it in recursive way.
All of this code below is only one method (vitoria):
(defun vitoria (tabuleiro)
(or (verificacaoXO (get-elem 1 1 1 tabuleiro)
(get-elem 1 1 2 tabuleiro)
(get-elem 1 1 3 tabuleiro))
(verificacaoXO (get-elem 1 2 1 tabuleiro)
(get-elem 1 2 2 tabuleiro)
(get-elem 1 2 3 tabuleiro))
(verificacaoXO (get-elem 1 3 1 tabuleiro)
(get-elem 1 3 2 tabuleiro)
(get-elem 1 3 3 tabuleiro))
columns between levels in position 1 - 3
(verificacaoXO (get-elem 2 1 1 tabuleiro)
(get-elem 2 1 2 tabuleiro)
(get-elem 2 1 3 tabuleiro))
(verificacaoXO (get-elem 2 2 1 tabuleiro)
(get-elem 2 2 2 tabuleiro)
(get-elem 2 2 3 tabuleiro))
(verificacaoXO (get-elem 2 3 1 tabuleiro)
(get-elem 2 3 2 tabuleiro)
(get-elem 2 3 3 tabuleiro))
columns between levels in position 2 - 6
(verificacaoXO (get-elem 3 1 1 tabuleiro)
(get-elem 3 1 2 tabuleiro)
(get-elem 3 1 3 tabuleiro))
(verificacaoXO (get-elem 3 2 1 tabuleiro)
(get-elem 3 2 2 tabuleiro)
(get-elem 3 2 3 tabuleiro))
(verificacaoXO (get-elem 3 3 1 tabuleiro)
(get-elem 3 3 2 tabuleiro)
(get-elem 3 3 3 tabuleiro))
columns between levels in position 3 - 9
(verificacaoXO (get-elem 1 1 1 tabuleiro)
(get-elem 1 2 2 tabuleiro)
(get-elem 1 3 3 tabuleiro))
(verificacaoXO (get-elem 1 3 1 tabuleiro)
(get-elem 1 2 2 tabuleiro)
(get-elem 1 1 3 tabuleiro))
lines between levels on top - 11
(verificacaoXO (get-elem 2 1 1 tabuleiro)
(get-elem 2 2 2 tabuleiro)
(get-elem 2 3 3 tabuleiro))
(verificacaoXO (get-elem 2 3 1 tabuleiro)
(get-elem 2 2 2 tabuleiro)
(get-elem 2 1 3 tabuleiro))
lines between levels in the middle - 13
(verificacaoXO (get-elem 3 1 1 tabuleiro)
(get-elem 3 2 2 tabuleiro)
(get-elem 3 3 3 tabuleiro))
(verificacaoXO (get-elem 3 3 1 tabuleiro)
(get-elem 3 2 2 tabuleiro)
(get-elem 3 1 3 tabuleiro))
lines between levels on bottom - 15
(verificacaoXO (get-elem 1 3 1 tabuleiro)
(get-elem 2 2 2 tabuleiro)
(get-elem 3 1 3 tabuleiro))
(verificacaoXO (get-elem 1 1 1 tabuleiro)
(get-elem 2 2 2 tabuleiro)
(get-elem 3 3 3 tabuleiro))
(verificacaoXO (get-elem 3 1 1 tabuleiro)
(get-elem 2 2 2 tabuleiro)
(get-elem 1 3 3 tabuleiro))
(verificacaoXO (get-elem 3 3 1 tabuleiro)
(get-elem 2 2 2 tabuleiro)
(get-elem 1 1 3 tabuleiro))
diagonal between levels - 19
(verificacaoXO (get-elem 1 1 1 tabuleiro)
(get-elem 1 2 1 tabuleiro)
(get-elem 1 3 1 tabuleiro))
(verificacaoXO (get-elem 2 1 1 tabuleiro)
(get-elem 2 2 1 tabuleiro)
(get-elem 2 3 1 tabuleiro))
(verificacaoXO (get-elem 3 1 1 tabuleiro)
(get-elem 3 2 1 tabuleiro)
(get-elem 3 3 1 tabuleiro))
lines on level 1 - 22
(verificacaoXO (get-elem 1 1 2 tabuleiro)
(get-elem 1 2 2 tabuleiro)
(get-elem 1 3 2 tabuleiro))
(verificacaoXO (get-elem 2 1 2 tabuleiro)
(get-elem 2 2 2 tabuleiro)
(get-elem 2 3 2 tabuleiro))
(verificacaoXO (get-elem 3 1 2 tabuleiro)
(get-elem 3 2 2 tabuleiro)
(get-elem 3 3 2 tabuleiro))
lines on level 2 - 25
(verificacaoXO (get-elem 1 1 3 tabuleiro)
(get-elem 1 2 3 tabuleiro)
(get-elem 1 3 3 tabuleiro))
(verificacaoXO (get-elem 2 1 3 tabuleiro)
(get-elem 2 2 3 tabuleiro)
(get-elem 2 3 3 tabuleiro))
(verificacaoXO (get-elem 3 1 3 tabuleiro)
(get-elem 3 2 3 tabuleiro)
(get-elem 3 3 3 tabuleiro))
lines on level 3 - 28
(verificacaoXO (get-elem 1 1 1 tabuleiro)
(get-elem 2 1 1 tabuleiro)
(get-elem 3 1 1 tabuleiro))
(verificacaoXO (get-elem 1 2 1 tabuleiro)
(get-elem 2 2 1 tabuleiro)
(get-elem 3 2 1 tabuleiro))
(verificacaoXO (get-elem 1 3 1 tabuleiro)
(get-elem 2 3 1 tabuleiro)
(get-elem 3 3 1 tabuleiro))
columns on level 1 - 31
(verificacaoXO (get-elem 1 3 2 tabuleiro)
(get-elem 2 1 2 tabuleiro)
(get-elem 3 1 2 tabuleiro))
(verificacaoXO (get-elem 1 2 2 tabuleiro)
(get-elem 2 2 2 tabuleiro)
(get-elem 3 2 2 tabuleiro))
(verificacaoXO (get-elem 1 3 2 tabuleiro)
(get-elem 2 3 2 tabuleiro)
(get-elem 3 3 2 tabuleiro))
columns on level 2 - 34
(verificacaoXO (get-elem 1 3 3 tabuleiro)
(get-elem 2 1 3 tabuleiro)
(get-elem 3 1 3 tabuleiro))
(verificacaoXO (get-elem 1 2 3 tabuleiro)
(get-elem 2 2 3 tabuleiro)
(get-elem 3 2 3 tabuleiro))
(verificacaoXO (get-elem 1 3 3 tabuleiro)
(get-elem 2 3 3 tabuleiro)
(get-elem 3 3 3 tabuleiro))
columns on level 3 - 37
(verificacaoXO (get-elem 1 1 1 tabuleiro)
(get-elem 2 2 1 tabuleiro)
(get-elem 3 3 1 tabuleiro))
(verificacaoXO (get-elem 1 3 1 tabuleiro)
(get-elem 2 2 1 tabuleiro)
(get-elem 3 1 1 tabuleiro))
diagonals of level 1 - 39
(verificacaoXO (get-elem 1 1 2 tabuleiro)
(get-elem 2 2 2 tabuleiro)
(get-elem 3 3 2 tabuleiro))
(verificacaoXO (get-elem 1 3 2 tabuleiro)
(get-elem 2 2 2 tabuleiro)
(get-elem 3 1 2 tabuleiro))
diagonals of level 2 - 41
(verificacaoXO (get-elem 1 1 3 tabuleiro)
(get-elem 2 2 3 tabuleiro)
(get-elem 3 3 3 tabuleiro))
(verificacaoXO (get-elem 1 3 3 tabuleiro)
(get-elem 2 2 3 tabuleiro)
(get-elem 3 1 3 tabuleiro))
diagonals of level 3 - 43
(verificacaoXO (get-elem 1 3 1 tabuleiro)
(get-elem 2 3 2 tabuleiro)
(get-elem 3 3 3 tabuleiro))
(verificacaoXO (get-elem 3 3 1 tabuleiro)
(get-elem 2 3 2 tabuleiro)
(get-elem 1 3 3 tabuleiro))
columns between levels on the right - 45
(verificacaoXO (get-elem 1 2 1 tabuleiro)
(get-elem 2 2 2 tabuleiro)
(get-elem 3 2 3 tabuleiro))
(verificacaoXO (get-elem 3 2 1 tabuleiro)
(get-elem 2 2 2 tabuleiro)
(get-elem 1 2 3 tabuleiro))
columns between levels on the middle - 47
(verificacaoXO (get-elem 1 1 1 tabuleiro)
(get-elem 2 1 2 tabuleiro)
(get-elem 3 1 3 tabuleiro))
(verificacaoXO (get-elem 3 1 1 tabuleiro)
(get-elem 2 1 2 tabuleiro)
(get-elem 1 1 3 tabuleiro))))
columns between levels on the middle - 49

Here is a possible solution, in which the coordinates are generated. Each point consists of three integer coordinates that identify a row, a column and a plane. A triple is a set of three points that determines a line. The triples are generate starting from a point and adding a direction twice (a vector like (0 1 0)). The triples that are not valid are eliminated.
(defun valid-coordinate(c)
(<= 1 c 3))
(defun valid(triple)
(loop for point in triple always (every #'valid-coordinate point)))
(defun add(point direction)
(mapcar #'+ point direction))
(defun make-triple(point direction)
(let ((pv (add point direction)))
(list point pv (add pv direction))))
(defun make-triples(point directions)
(loop for d in directions
as triple = (make-triple point d)
when (valid triple)
collect triple))
(defun make-all-triples ()
(let ((directions-on-plane '((0 1 0)(1 0 0)(1 1 0)(-1 -1 0)))
(3d-directions '((0 0 1)(0 1 1)(1 0 1)(1 1 1)(-1 0 1)(0 -1 1)(-1 -1 1)(1 -1 1)(-1 1 1))))
(nconc (loop for plane from 1 to 3
nconc (loop for r from 1 to 3
nconc (loop for c from 1 to 3
nconc (make-triples (list r c plane) directions-on-plane))))
(loop for r from 1 to 3
nconc (loop for c from 1 to 3
as plane = 1
nconc (make-triples (list r c plane) 3d-directions))))))
(defun vitoria (tabuleiro)
(loop for triple in (make-all-triples)
thereis (apply #'verificacaoXO (loop for (r c plane) in triple
collect (get-elem r c plane tabuleiro)))))

Related

KDB Select average of List data type for each row

Is there anyway in KDB to get the average of each row which has list data type ?
E.g. I have table with column ID and Size :
| ID | size |
|----|-----------|
| 1 | [1,3] |
| 2 | [3,3,3] |
| 3 | [4,2,4,2] |
In select , I want ID and avg of size :
| ID | avg |
|----|-----|
| 1 | 2 |
| 2 | 3 |
| 3 | 3 |
q)t:([]id:1 2 3;size:(1 3;3 3 3;4 2 4 2))
q)t
id size
----------
1 1 3
2 3 3 3
3 4 2 4 2
q)select id,avg each size from t
id size
-------
1 2
2 3
3 3

Dynamically enumerate object from vertical to horizontal

I have got data with PowerShell into a object as below, now i would like to convert it from vertical to horizontal. (Like "Text to column" function in Excel). How can I dynamically enumerate "all row 1" as an object header and the rest of them will assign to its child items?
The input file contains three columns, "Row", "Column" and "Text", in PSObject
PS > $table
Row Column Text
--- ------ ----
1 1 Dept
1 2 Time
1 3 Day1
1 4 Day2
1 5 Day3
1 6 Day4
1 7 Day5
1 8 Day6
1 9 Day7
2 1 Marketing
2 2 11:00
2 3 4
2 4 8
2 5 8
2 6 8
2 7 4
2 8 0
2 9 0
3 1 Finance
3 2 09:00
3 3 4
3 4 8
3 5 8
3 6 8
3 7 4
3 8 0
3 9 0
I tried to use the following code to assign it into another object, but I don't know how to let the content put in.
$data = New-Object –TypeName PSObject
$table | %{
if ($_.row -eq 1) {
$data | Add-Member –MemberType NoteProperty –Name $_.text –Value ''
}
}
Output:
PS > $data|ft
Dept Time Day1 Day2 Day3 Day4 Day5 Day6 Day7
---- ---- ---- ---- ---- ---- ---- ---- ----
Expected result:
Dept Time Day1 Day2 Day3 Day4 Day5 Day6 Day7
---- ---- ---- ---- ---- ---- ---- ---- ----
Marketing 11:00 4 8 8 8 4 0 0
Finance 09:00 4 8 8 8 4 0 0
There is a need for some kind of indirect reference. You can do the following:
$dataLabels = New-Object –TypeName psobject
$dataZero = New-Object –TypeName psobject
$data = #() ### or ### New-Object System.Collections.ArrayList
$table | Where-Object { $_.row -eq 1 } | ForEach-Object {
$dataLabels |
Add-Member –MemberType NoteProperty –Name $_.Column –Value $_.Text
$dataZero |
Add-Member –MemberType NoteProperty –Name $_.Text –Value ''
}
$dataZeroCsv = $dataZero | ConvertTo-Csv -NoTypeInformation
for ( $i=0;$i -lt ($Table.Row|Measure-Object -Maximum).Maximum -1;$i++)
{
$dataLine = $dataZeroCsv | ConvertFrom-Csv
$table | Where-Object { ($_.Row - 2) -eq $i } |
ForEach-Object {
$dataLine.($dataLabels.($_.Column)) = $_.Text ### indirect reference
}
$data += $dataLine ### or ### [void]$data.Add( $dataLine )
}
## Output:
$data | Format-Table
provided that $table is defined as follows:
$tableArr = #"
Row Column Text
1 1 Dept
1 2 Time
1 3 Day1
1 4 Day2
1 5 Day3
1 6 Day4
1 7 Day5
1 8 Day6
1 9 Day7
2 1 Marketing
2 2 11:00
2 3 4
2 4 8
2 5 8
2 6 8
2 7 4
2 8 0
2 9 0
3 1 Finance
3 2 09:00
3 3 3
3 4 4
3 5 5
3 6 6
3 7 7
3 8 0
3 9 1
4 1 TestDept
4 2 16:00
4 4 5
"# -split [System.Environment]::NewLine
$table = $tableArr -replace '\s+', ' ' -replace '^\s', '' |
ConvertFrom-Csv -Delimiter ' '
Output:
PS D:\PShell> D:\PShell\SO\52804963.ps1
Dept Time Day1 Day2 Day3 Day4 Day5 Day6 Day7
---- ---- ---- ---- ---- ---- ---- ---- ----
Marketing 11:00 4 8 8 8 4 0 0
Finance 09:00 3 4 5 6 7 0 1
TestDept 16:00 5

postgresql select max no if date is same

i have a table like:
sr_no or_no date
1 1 2017-01-01
1 2 2017-02-02
1 3 2017-02-02
2 1 2017-01-02
2 2 2017-01-10
What i want is if date field for a sr_no is same then record with max or_no should be fetched. Output should be like:
sr_no or_no date
1 1 2017-01-01
1 3 2017-02-02
2 1 2017-01-02
2 2 2017-01-10
just distinct on to cut max(or_no) with order:
with a as (select distinct on (d) * from t order by d,or_no desc)
select * from a order by sr_no,or_no;
sr_no | or_no | d
-------+-------+------------
1 | 1 | 2017-01-01
1 | 3 | 2017-02-02
2 | 1 | 2017-01-02
2 | 2 | 2017-01-10
(4 rows)

Postgresql GROUB BY combination

Hi I have a problem with the group by clause if I have combinations between,
This is a part from my table with combinations:
CREATE TABLE sampleTable
(
id serial primary key,
sat1 varchar(3),
sat2 varchar(3)
);
INSERT INTO sampleTable
(sat1, sat2)
VALUES
('LE7','LE7'),
('LE8','LE7'),
('LE7','LE7'),
('LE7','LC8'),
('LE7','LE8'),
('LE8','LE7'),
...
http://sqlfiddle.com/#!15/63104/2
I search the count of combinations, but for me the combination sat1,sat2 is the same like sat2,sat1.
My (wrong) SQL-Code:
select sat1, sat2, count(*) from sampleTable group by sat1, sat2 order by sat1
and the result:
sat1 sat2 count
1 LC8 LC8 27
2 LC8 LE7 17
3 LE7 LE7 200
4 LE7 LC8 22
5 LM1 LM2 2
6 LM1 LM1 12
7 LM2 LM2 6
8 LM2 LM1 3
but it should by:
sat1 sat2 count
1 LC8 LC8 27
2 LC8 LE7 39 (17+22 / line 2 & 4)
3 LE7 LE7 200
4 LM1 LM2 5 (2+3 / line 5 & 8)
5 LM1 LM1 12
6 LM2 LM2 6
Has anyone a SQL-Code which solved my question?
Thanks for Help!!
Use LEAST() and GREATEST() to "simplify" the 2 grouping columns:
Query 1:
select least(sat1, sat2), greatest(sat1, sat2), count(*)
from sampleTable
group by least(sat1, sat2), greatest(sat1, sat2)
order by least(sat1, sat2)
[Results][2]:
| least | greatest | count |
|-------|----------|-------|
| LC8 | LC8 | 27 |
| LC8 | LE7 | 39 |
| LE7 | LE7 | 200 |
| LM1 | LM1 | 12 |
| LM1 | LM2 | 5 |
| LM2 | LM2 | 6 |
See this SQL Fiddle

Get column a and column b through first parameter to last parameter

I'm newbie on tsql and stuck on this problem. Can anyone help this prb?
I have a table like below; (use SQL 2008 Express Edt.)
ID COL1 COL2
1 7 2
2 7 3
3 7 4
4 7 5
5 9 2
6 9 3
7 9 4
8 9 5
9 11 2
10 11 3
11 11 4
12 11 5
how to use select query to fetch between 7/3 and 11/2 (both columns and first/last rows included)
SQL Fiddle
MS SQL Server 2008 Schema Setup:
create table YourTable
(
ID int,
COL1 int,
COL2 int
)
insert into YourTable values
(1 ,7 ,2),
(2 ,7 ,3),
(3 ,7 ,4),
(4 ,7 ,5),
(5 ,9 ,2),
(6 ,9 ,3),
(7 ,9 ,4),
(8 ,9 ,5),
(9 ,11 ,2),
(10 ,11 ,3),
(11 ,11 ,4),
(12 ,11 ,5)
Query 1:
select *
from YourTable
where (COL1 > 7 and COL1 < 11) or
(COL1 = 7 and COL2 >= 3) or
(COL1 = 11 and COL2 <= 2)
Results:
| ID | COL1 | COL2 |
--------------------
| 2 | 7 | 3 |
| 3 | 7 | 4 |
| 4 | 7 | 5 |
| 5 | 9 | 2 |
| 6 | 9 | 3 |
| 7 | 9 | 4 |
| 8 | 9 | 5 |
| 9 | 11 | 2 |