Django Exclude Model Objects from query using a list - django

Having trouble with my query excluding results from a different query.
I have a table - Segment that I have already gotten entries from. It is related
to another table - Program, and I want to also run the same query on it but I want to exclude
any of the programs that were already found during the segment query.
When I try to do it, the list isn't allowed to be used in the comparison... See below:
query = "My Query String"
segment_results = Segment.objects.filter(
Q(title__icontains=query)|
Q(author__icontains=query)|
Q(voice__icontains=query)|
Q(library__icontains=query)|
Q(summary__icontains=query) ).distinct()
# There can be multiple segments in the same program
unique_programs = []
for segs in segment_results:
if segs.program.pk not in unique_programs:
unique_programs.append(segs.program.pk)
program_results = ( (Program.objects.filter(
Q(title__icontains=query) |
Q(library__icontains=query) |
Q(mc__icontains=query) |
Q(producer__icontains=query) |
Q(editor__icontains=query) |
Q(remarks__icontains=query) ).distinct()) &
(Program.objects.exclude(id__in=[unique_programs])))
I can run:
for x in unique_programs:
p = Program.objects.filter(id=x)
print("p = %s" % p)
And I get a list of Programs...which works
Just not sure how to incorporate this type of logic into the results
query...and have it exclude at the same time. I tried exclude keyword,
but the main problem is it doesn't like the list being in the query - I get an
error:
TypeError: int() argument must be a string, a bytes-like object or a number, not 'list'.
Feel like I am close...

The answer is simple, I was not comparing objects correctly in the filters, so
the correct statement would be:
program_results = (Program.objects.filter(
Q(title__icontains=query) |
Q(library__icontains=query) |
Q(mc__icontains=query) |
Q(producer__icontains=query) |
Q(editor__icontains=query) |
Q(remarks__icontains=query) )&
(Program.objects.exclude(id__in=Program.objects.filter(id__in=unique_programs))))

Related

How to conditionally transform text in a column in power query?

I am building a workbook in PowerBI and I have the need for doing a conditional appending of text to column A if it meets a certain criteria. Specifically, if column A does not end with ".html" then I want to append the text ".html" to the column.
A sample of the data would look like this:
URL | Visits
site.com/page1.html | 5
site.com/page2.html | 12
site.com/page3 | 15
site.com/page4.html | 8
where the desired output would look like this:
URL | Visits
site.com/page1.html | 5
site.com/page2.html | 12
site.com/page3.html | 15
site.com/page4.html | 8
I have tried using the code:
#"CurrentLine" = Table.TransformColumns(#"PreviousLine", {{"URL", each if Text.EndsWith([URL],".html") = false then _ & ".html" else "URL", type text}})
But that returns an error "cannot apply field access to the type Text".
I can achieve the desired output in a very roundabout way if I use an AddColumn to store the criteria value, and then another AddColumn to store the new appended value, but this seems like an extremely overkill way to approach doing a single transformation to a column. (I am specifically looking to avoid this as I have about 10 or so transformations and don't want to have so many columns to add and cleanup if there is a more succinct way of coding)
You don't want [URL] inside Text.EndWith. Try this:
= Table.TransformColumns(#"PreviousLine",
{{"URL", each if Text.EndsWith(_, ".html") then _ else _ & ".html", type text}}
)

How to optimize regexp_replace performance for multiple substrings in PostgreSQL

I need to remove multiple substrings from a column of strings. I have ~200k rows, as well as a large bag of custom "stopwords."
Specifically, I have a table (NameTable), with a Names column full of multiple-word strings. Only a small subset of the words in each string is relevant for what I'm doing next. names has a trigram/GIN index. Is there any way to speed up a query like the following, but with a much larger string of target words? I'm using PG10.
...
Create Index Names_trgm on NameTable using gin(Name gin_trgm_ops);
Update NameTable
set CleanedName = regexp_replace(Name, '( fuzzy| wuzzy| was| a | bear | the |
first| time | yossarian| saw | the | chaplain | he | fell| madly| in | love|
with| him)',' ','g');

Making query from a list with varying amount of values

I have for example the following lists:
list1 = ['blue', 'red']
list2 = ['green', 'yellow', 'black']
How could i create a query searching for all values (using postgresql).
This will work fine but it's hardcoded for only two values and therefore not handling the varying amount of values of the lists.
entry.objects.annotate(search=SearchVector('colors')).filter(search=SearchQuery('blue') | SearchQuery('red'))
I tried the following to create a 'search_query' string and place it in my query:
for c in color:
search_string += "SearchQuery('" + c +"') | "
search_string = search_string[:-3]
This will result in the following search_strings
SearchQuery('blue') | SearchQuery('red')
SearchQuery('green') | SearchQuery('yellow') | SearchQuery('black')
If i now put this string in my query, it will not work.
entry.objects.annotate(search=SearchVector('colors')).filter(search=search_string)
I appreciate any help to solve this problem.
Link to django postgres search documentation: https://docs.djangoproject.com/en/1.11/ref/contrib/postgres/search/
I don't know about postgreSQL but:
# Can run this query with SQL (i think django query auto convert for each type of DataBase???)
res = Models.Objects.filter(color__in = list1)
more_res = Models.Objects.filter( Q(color__in = list1) | Q(color__in = list2))
Django query basic (i don't know if it work for you???)
Your search_string is not working because it is, well, a string.
You can use eval to make it work. Try this:
entry.objects.annotate(search=SearchVector('colors')).filter(search=eval(search_string))
It is not the best way though. Take a look at this

Combine Q objects in Django and limit one of them

I want to combine these 2 queries in 1 to get the Music object with name xyz and also get top 3 objects from genre 10, ordered by artist:
1. Music.objects.filter(name='xyz', genre=10)
2. Music.objects.filter(genre=10).order_by('artist')[:3]
I can use Q objects like this but I don't know how to order & filter the 3rd Q object below:
Music.objects.filter( (Q(name='xyz') & Q(genre=10)) | Q(genre=10) )
Maybe try like this?
Music.objects.filter( (Q(name='xyz') & Q(genre=10)) | Q(genre=10) ).order_by('artist')[:3]
No way to do it, use two queries but change second to avoid duplicates:
exact = Music.objects.filter(name='xyz', genre=10)
additional = Music.objects.filter(genre=10).exclude(name='xyz').order_by('artist')[:3]
do_something_with = list(exact) + list(additional)

Getting error: Prelude.(!!): index too large

I'm getting this 'program: Prelude.(!!): index too large' error for the following code:
select :: Field -> Field -> Table -> Table
select column_name column_value (header:t) = header:filterT t
where filterT = filter testR
field_idx = (elemIndices column_name header)!!0
testR r | r!!field_idx == column_value = True
testR r | otherwise = False
I suppose the error is regarding the following part of the code:
field_idx = (elemIndices column_name header)!!0
testR r | r!!field_idx == column_value = True
Does anyone know why it's giving me this error or how I could fix it?
I'm not sure what you're doing, but I hope you're aware, that !! is not a safe operation. an element with the index doesn't necessarily exist.
So you could get this error, if, for example, the header doesn't contain column_name.
Again, not sure what you exactly want to do, but if there's a chance there's no result, perhaps you want to wrap the result with Maybe?