[0610] TIL 44์ผ์ฐจ

nikevapormaxยท2022๋…„ 6์›” 10์ผ
0

TIL

๋ชฉ๋ก ๋ณด๊ธฐ
44/116
post-custom-banner

๐Ÿ˜‚ Django Project

๐Ÿ˜ญ Post App

- ์ž‘์„ฑ๋œ ๊ฒŒ์‹œ๋ฌผ ๋‚ด์šฉ ํ™•์ธ

  • ์ž‘์„ฑ๋œ ๊ฒŒ์‹œ๋ฌผ์˜ ์ œ๋ชฉ, ํ‰์ , ์ž‘์„ฑ์‹œ๊ฐ„์„ ํ™•์ธํ•  ์ˆ˜ ์žˆ์—ˆ์œผ๋‚˜ ํ•ด๋‹น ๋‚ด์šฉ์„ ํ™•์ธํ•˜๊ณ  ์ˆ˜์ •ํ•˜๋Š” ๋ถ€๋ถ„์ด ํ•„์š”ํ•˜๋‹ค๋Š” ์˜๊ฒฌ์ด ๋‚˜์™€ ์ž‘์—…

  • ๊ฒŒ์‹œ๋ฌผ์„ ์ž‘์„ฑํ•  ๋•Œ ์‚ฌ์šฉํ–ˆ๋˜ ์ฃผํ˜„๋‹˜์ด ๋งŒ๋“  ํŽ˜์ด์ง€์™€ ๋™์ผํ•œ UI๋ฅผ ์‚ฌ์šฉํ•ด ์‚ฌ์šฉ์ž๊ฐ€ ์ˆ˜์ •์„ ์นœ์ˆ™ํ•˜๊ฒŒ ํ•  ์ˆ˜ ์žˆ๋„๋ก ์ž‘์„ฑ

  • ์‚ฌ์šฉ์ž๊ฐ€ ์ด๋ฏธ ์ž‘์„ฑํ•œ ๋‚ด์šฉ์„ ๊ธฐ๋ณธ ๋‚ด์šฉ์œผ๋กœ ๊ฐ€์ง€๊ณ  ์žˆ์–ด์•ผ ํ•˜๋ฉฐ, ์‚ฌ์šฉ์ž๊ฐ€ ์–ด๋–ค ๊ฐ’์œผ๋กœ ๋ฐ”๊พธ๋Š”์ง€ ํ™•์ธํ•  ์ˆ˜ ์žˆ๋„๋ก ๋ฐ”๋€Œ๋Š” ํ‰์  ๊ฐ’์„ ํ‘œ์‹œ

  • ์ทจ์†Œ ํ‚ค๋ฅผ ๋ˆ„๋ฅด๋ฉด ๊ฒŒ์‹œ๋ฌผ ๋ฆฌ์ŠคํŠธ๊ฐ€ ์žˆ๋Š” mypage๋กœ ๋‹ค์‹œ ๋Œ์•„๊ฐˆ ์ˆ˜ ์žˆ๋„๋ก location.href๋ฅผ ์‚ฌ์šฉ

    • ํ˜„์žฌ ๋‹จ๊ณ„์˜ ํ”„๋กœ์ ํŠธ์—์„œ๋Š” form ํƒœ๊ทธ๋ฅผ ์“ธ ์ˆ˜ ๋ฐ–์— ์—†๊ณ , form ํƒœ๊ทธ์˜ ๋‚ด์šฉ์„ ๋ฐฑ์•ค๋“œ๋กœ ๋ณด๋‚ด๋Š” ๋ฒ„ํŠผ์€ ๋”ฐ๋กœ ์žˆ์—ˆ๊ธฐ ๋•Œ๋ฌธ์— ํ•ด๋‹น ๊ฒฐ์ • ๋‚ด๋ฆผ
    • ๋˜ํ•œ ์ทจ์†Œ๋ผ ๋”ฐ๋กœ ๋ณด๋‚ผ ๋‚ด์šฉ์ด ์—†์–ด ๋”๋”์šฑ ์ƒ๊ด€์—†๋‹ค๊ณ  ํŒ๋‹จ
  • ์ž‘์„ฑ์‹œ๊ฐ„์—๋„ ๋ณ€ํ™”๊ฐ€ ์žˆ์œผ๋ฉด ์ข‹์„ ๊ฒƒ ๊ฐ™์•„ datetime ๋ชจ๋“ˆ์˜ datetime.datetime.now()๋ฅผ ์‚ฌ์šฉํ•ด ํ˜„์žฌ ๋ณ€๊ฒฝ ์‹œ๊ฐ„์„ ์ €์žฅํ•ด ์คŒ

  • ์ฝ”๋“œ

    • post/urls.py

      from django.urls import path
       from . import views
       urlpatterns = [
            path('detail/edit/<int:id>/', views.edit, name='edit'),
      	  path('detail/update/<int:id>', views.update, name='update'),
       ]
    • post/views.py

      from django.shortcuts import render, redirect
      from .models import PostModel
      from movie.models import Movie
      from datetime import datetime
      
      
      # ๊ฒŒ์‹œ๋ฌผ ํ™•์ธ
      def edit(request, id):
          article = PostModel.objects.get(id=id)
          movie = Movie.objects.get(id=article.title_id)
      
          context = {
             'article': article,
             'movie': movie,
          }
      
          return render(request, 'post/edit.html', context)
          
      # ๊ฒŒ์‹œ๋ฌผ ์—…๋ฐ์ดํŠธ
      def update(request, id):
          if request.method == 'POST':
              user = request.user
      
              article = PostModel.objects.get(id=id)
              article.score = request.POST.get('myRange')
              article.content = request.POST.get('comment')
              article.created_at = datetime.now()
              article.save()
      
              all_post = PostModel.objects.filter(author_id=user.id).order_by('-created_at')
      
              return render(request, 'post/mypage.html', {'username': user, 'posts': all_post})
    • templates/post/edit.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Edit</title>
</head>

<body>
    <div class="modal" id="modal">
        <div class="modal_back">
            <div class="modal_content">
                <div class="modal_title">
                    ๊ฒŒ์‹œ๊ธ€ ์ˆ˜์ •
                </div>
                <form action="/detail/update/{{ article.id }}" method="POST">
                    {% csrf_token %}
                     <div class="modal_component">
                        <div class="title">
                            {{ movie.title }}
                        </div>
                        <div>
                            <div class="slidecontainer" >
                                <span>ํ‰์ ์„ ๋ฐ”๊ฟ”์ฃผ์„ธ์š”.</span><br>
                                <input required type="range" min="1" max="5" step="0.1" value="{{ article.score }}" class="slider" id="myRange" name="myRange" oninput="document.getElementById('score').innerHTML=this.value;" ><br>
                                <span id="score" class="score">{{ article.score }}</span>
                            </div>
                        </div>
                        <div>
                            <textarea required name="comment" id="comment" class="comment" placeholder="">{{ article.content }}</textarea>
                        </div>
                        <div>
                            <button type="button" onclick="location.href='/mypage'" class="btn1" id="btn1">์ทจ์†Œ</button> <button class="btn2" type="submit">์ž‘์„ฑ</button>
                        </div>
                    </div>
                </form>
            </div>
        </div>
    </div>


</body>
</html>

๐Ÿ˜ญ item-based collaborative filtering

  • ์›๋ž˜์˜ ์ปจ์…‰์€ ๊ฐ ์žฅ๋ฅด๋ณ„๋กœ ์œ ๋ช…ํ•œ ์˜ํ™”๋ฅผ ํ•˜๋‚˜์”ฉ ์ฃผ๊ณ  ์‚ฌ์šฉ์ž๊ฐ€ ์„ ํƒํ•˜๊ฒŒ ํ•˜๋ฉฐ, ์„ ํƒํ•œ ๊ฐ’์— ๋”ฐ๋ผ ํ•„ํ„ฐ๋งํ•œ ์˜ํ™”๋“ค์„ ์ฃผ๋Š” ๊ฒƒ์ด์—ˆ๋‹ค. ํ•˜์ง€๋งŒ ์•„์ง์€ ์žฅ๋ฅด๋ฅผ ๊ฐ€์ง€๊ณ  ๋‚˜๋ˆ„์ง€๋Š” ๋ชปํ–ˆ๋‹ค.
  • ๊ตฌ๊ธ€ ์ฝ”๋žฉ์—์„œ ์ž‘์„ฑํ•œ ์ฝ”๋“œ๋ฅผ ๊ฐ€์ ธ์™€ ํ•จ์ˆ˜๋กœ ์„ ์–ธํ•ด ์ฃผ๊ณ , ํ•ด๋‹น ํ•จ์ˆ˜๋ฅผ ํ˜ธ์ถœํ•ด ํ•„ํ„ฐ๋ง์„ ๋Œ๋ฆฌ๋Š” ๋ฐฉ์‹์œผ๋กœ ์ฝ”๋”ฉ์„ ํ–ˆ๋‹ค.
  • recommend/views.py
from django.shortcuts import render, redirect
import pandas as pd
from sklearn.metrics.pairwise import cosine_similarity
from movie.models import Movie, Taste

movies = pd.read_csv('recommend/movies.csv')
ratings = pd.read_csv('recommend/ratings.csv')

### item_based_filtering ####
movie_ratings = pd.merge(ratings, movies, on='movieId')

user_title = movie_ratings.pivot_table(
    'rating', index='title', columns='userId')
user_title = user_title.fillna(0)

item_based_collab = cosine_similarity(user_title, user_title)
item_based_collab = pd.DataFrame(
    item_based_collab, index=user_title.index, columns=user_title.index)

def item_based_filtering(movie):
    # ์ฃผ์–ด์งˆ ์˜ํ™” ์ค‘ cosine-similarity ๊ฐ’์ด ๊ฐ€์žฅ ํฐ ์ˆœ์œผ๋กœ 20๋ฒˆ์งธ๊นŒ์ง€ ๋ณ€์ˆ˜์— ์ €์žฅ
    movie_list = item_based_collab[movie].sort_values(ascending=False)[1:21]
    print(f'movie_list : {movie_list.index}')
    
    return movie_list.index


def taste(request):
    if request.method == 'POST':
        user = request.user
        print(f'user:{user}')
        print(user.id)

        for key, value in request.POST.items():
            if key == "csrfmiddlewaretoken":
                continue
            else:

                Taste.objects.create(
                    user=user,
                    # movie=Movie.objects.get(title=value),
                    movie_id=value,
                )

                movies = []

                movie = Movie.objects.get(id=value)
                print(movie.title)
                a = item_based_filtering(movie.title)
                for i in a:
                    movie = Movie.objects.get(title=i)
                    movie.tags = ", ".join(
                        list(movie.tag.all().values_list('tag', flat=True)))
                    movies.append(movie)
                print(movies, type(movies))
            return render(request, 'movie/home.html', {'movies': movies})
  • templates/recommend/taste.html
{% extends 'base.html' %}


{% block content %}
    <form action="{% url 'recommend:taste' %}"  method="post">
    {% csrf_token %}
        {% if movies %}
            {% for movie in movies %}
                <div>
                    <input type="checkbox" name="title" value="{{ movie.id }}">
                    <label for="title">{{ movie.title }}</label>
                </div>
            {% endfor %}
        {% endif %}
        <button type="submit">OK</button>
    </form>
{% endblock %}
profile
https://github.com/nikevapormax
post-custom-banner

0๊ฐœ์˜ ๋Œ“๊ธ€